Sixty years since Silent Spring: towards a balanced view of the organochlorine pesticide literature

Kyle Morrison, Coralie Williams, Lorenzo Ricolfi, Yefeng Yang, Malgorazata Lagisz, Shinichi Nakagawa

2023-03-09

In this Rmarkdown document we provide the following workflow:

  • Objective 0 - To examine the volume and temporal trends of existing meta-analyses on the effects of organochlorine pesticides

  • Objective 1: To evaluate the methodological patterns and quality of existing meta-analyses studying the effects of organochlorine pesticides.

  • Objective 2 . To explore the various characteristics of the organochlorine pesticides literature such as the pesticides used, the impacts elicited in response and the subjects that were investigated.

  • Objective 4 - To investigate the research outputs across different countries and continents and investigate the degree of cross-country collaboration.

Load packages and data

Load Packages

rm(list = ls())
pacman::p_load(tidyverse,
hrbrthemes, 
patchwork,
here,
stringr,
knitr,
formatR,
forcats,
ggplot2,
bibliometrix,
igraph,
stringi,
stringdist,
circlize,
ggalluvial,
ggraph)
knitr::opts_chunk$set(echo = TRUE, message = FALSE, warning = FALSE)

Load data

Manually extracted pilot data is stored in five separate .csv files representing different aspects of the data (extracted via structured predefined Google Forms - one per table).

Bibliographic data records are exported from Scopus (including cited references field) in .bib format and locally saved as scopus.bib.

# Load CSV datasets
sd <- read_csv(here("data", "ocp_srm_study_details.csv"))
ocp <- read_csv(here("data", "ocp_srm_ocp_details.csv"))
sub <- read_csv(here("data", "ocp_srm_subject_details.csv"))
im <- read_csv(here("data", "ocp_srm_impact_details.csv"))
sp <- read_csv(here("data", "ocp_srm_species_details.csv"))

# Load BibTeX dataset
bib_sco <- convert2df(here("data", "bib_sco.bib"), dbsource = "scopus", format = "bibtex")
## 
## Converting your scopus collection into a bibliographic dataframe
## 
## Done!
## 
## 
## Generating affiliation field tag AU_UN from C1:  Done!

Objective 1: To evaluate the methodological patterns and quality of existing meta-analyses studying the effects of organochlorine pesticides.

Figure s5

A bar plot showing the percentage and total count of scientific literature databases used in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple scientific literature databases. “Other databases” is all other databases with a count less than or equal to 3

# Calculate the total count for each category
database_count <- sd %>% 
  separate_rows(database_search, sep = ",\\s+") %>% 
  count(database_search) %>% 
  filter(database_search != "not reported") %>% 
  arrange(desc(n)) %>% 
  mutate(database_search = ifelse(n<= 3, "Other databases", as.character(database_search))) %>% 
    group_by(database_search) %>%
  summarise(n = sum(n))


# Calculate proportion and percentage for each category
database_pct <- database_count %>%
  mutate(proportion = n / sum(database_count$n),
         percentage = proportion * 100)

# Create a standard theme for the supplement plots
theme_suppl <- function() {
  theme_minimal() +
  theme(
    axis.text.y = element_text(size = 15),
    axis.text.x = element_text(size = 15),
    axis.line.x = element_line(color = "gray", size = 0.5),
    axis.line.y = element_blank(),
    axis.ticks.x = element_blank(),
    axis.ticks.y = element_blank(),
    axis.title.x = element_text(size = 20),
    axis.title.y = element_text(size = 20),
    panel.grid.major.y = element_blank(),
    panel.grid.minor.y = element_blank(),
    legend.position = "none"
  )
}

# Create the count plot
figs5 <- database_count %>%
  ggplot(aes(x = n, y = reorder(database_search, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(database_search, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = database_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_y_discrete(name = "Database Search") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(database_count$n)*1.1)) +
  labs(y = NULL) +
  theme_suppl()

figs5

  ggsave(here("figures", "figs5.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
  ggsave(here("figures", "figs5.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s6

An alluvial plot showing the relationship between the Journal Citation Report Category and the scientific literature database used. Filtered for scientific literature database counts greater than or equal to 3

# Rename Environmental Science
sd <- sd %>%
  mutate(Journal_Category_Allocated_Broad = str_replace(Journal_Category_Allocated_Broad, "Environmental Science", "Environmental\nScience"))

# Data Transformation 
database_alluvial <- sd %>% 
    separate_rows(database_search, sep = ",\\s+") %>%
    group_by(Journal_Category_Allocated_Broad, database_search) %>% 
    count(database_search, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(database_search) %>% 
    filter(sum(freq) >= 3) %>% 
    filter(database_search != "NA")

# Create the Alluvial plot
figs6 <- database_alluvial %>% 
ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = database_search)) +
  scale_x_discrete(limits = c("Journal Citation Report Category", "Database Search"), expand = c(.05, .05)) +
  xlab("Variables") +
  ylab("Frequency") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4.5, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()

figs6

 ggsave(here("figures", "figs6.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs6.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s7

A bar plot showing the percentage and total count of effect size calculation type used in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple effect size calculations. “Other effect sizes” is all other effect sizes with a count less than or equal to 2

# Calculate the total count for each category
effectsize_count <- sd %>% 
  separate_rows(effect_size, sep = ",\\s+") %>% 
  count(effect_size) %>%
  filter(effect_size != "NA") %>%
  mutate(effect_size = ifelse(n<= 2, "Other effect sizes", as.character(effect_size))) %>% 
  group_by(effect_size) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
effectsize_pct <- effectsize_count %>%
  mutate(proportion = n / sum(effectsize_count$n),
         percentage = proportion * 100)

# Create the count plot
figs7 <-  effectsize_count %>%
  ggplot(aes(x = n, y = reorder(effect_size, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(effect_size, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = effectsize_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(effectsize_count$n)*1.1)) +
  labs(y = NULL) +
  theme_suppl()

figs7

  ggsave(here("figures", "figs7.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
  ggsave(here("figures", "figs7.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s8

An alluvial plot showing the relationship between the Journal Citation Report Category and the effect size used.

# Data Transformation 
effectsize_alluvial <- sd %>% 
    separate_rows(effect_size, sep = ",\\s+") %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>% 
    filter(!grepl("no category found", Journal_Category_Allocated_Broad, ignore.case = TRUE)) %>% 
    filter(!is.na(effect_size)) %>%
    group_by(Journal_Category_Allocated_Broad, effect_size) %>% 
    count(effect_size, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(effect_size) 


# Create the Alluvial plot
figs8 <- effectsize_alluvial %>% 
ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = effect_size)) +
  scale_x_discrete(limits = c("Journal Category", "Effect Size"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4.5, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  theme_minimal() +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()
  
figs8

 ggsave(here("figures", "figs8.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs8.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s9

A bar plot showing the percentage and total count of software for analysis in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple softwares

# Calculate the total count for each category
software_count <- sd %>%
  separate_rows(software_analysis, sep = ",\\s+") %>%
  mutate(software_analysis = ifelse(grepl("comprehensive meta-analysis", software_analysis), "CMAS", software_analysis)) %>%
  mutate(software_analysis = ifelse(grepl("not reported", software_analysis), "no software reported", software_analysis))  %>% 
  count(software_analysis) %>%
  filter(software_analysis != "NA") %>%
  group_by(software_analysis) %>%
  summarise(n = sum(n))


# Calculate proportion and percentage for each category
software_pct <- software_count %>%
  mutate(proportion = n / sum(software_count$n),
         percentage = proportion * 100)

# Create the count plot
figs9 <- software_count %>%
  ggplot(aes(x = n, y = reorder(software_analysis, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(software_analysis, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = software_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(software_count$n)*1.1)) +
  labs(y = NULL) +
  theme_suppl()

figs9

 ggsave(here("figures", "figs9.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs9.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s10

An alluvial plot showing the relationship between the Journal Citation Report Category and the software used for analysis.

# Data Transformation 
software_analysis_alluvial <- sd %>% 
    separate_rows(software_analysis, sep = ",\\s+") %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>% 
  mutate(software_analysis = ifelse(grepl("comprehensive meta-analysis", software_analysis), "CMAS", software_analysis)) %>%
  mutate(software_analysis = ifelse(grepl("not reported", software_analysis), "no software reported", software_analysis))  %>% 
    filter(!is.na(software_analysis)) %>%
    group_by(Journal_Category_Allocated_Broad, software_analysis) %>% 
    count(software_analysis, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(software_analysis)

# Create the Alluvial plot for Software Analysis
figs10 <- software_analysis_alluvial %>% 
ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = software_analysis)) +
  scale_x_discrete(limits = c("Journal Category", "Software Analysis"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()

figs10

 ggsave(here("figures", "figs10.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs10.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s11

A bar plot showing the percentage and total count of heterogeneity assessment in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple heterogeneity assessments

# Calculate the total count for each category
heterogeneity_count <- sd %>% 
  separate_rows(heterogeneity_assessment_method, sep = ",\\s+") %>% 
  count(heterogeneity_assessment_method) %>%
    mutate(heterogeneity_assessment_method = ifelse(grepl("not reported", heterogeneity_assessment_method), "no heterogeneity\nmeasure reported", heterogeneity_assessment_method))  %>% 
  filter(heterogeneity_assessment_method != "NA") %>%
    group_by(heterogeneity_assessment_method) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
heterogeneity_pct <- heterogeneity_count %>%
  mutate(proportion = n / sum(heterogeneity_count$n),
         percentage = proportion * 100)

# Create the count plot
figs11 <- heterogeneity_count %>%
  ggplot(aes(x = n, y = reorder(heterogeneity_assessment_method, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(heterogeneity_assessment_method, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = heterogeneity_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(heterogeneity_count$n)*1.1)) +
  labs(y = NULL) +
  theme_suppl()

figs11

 ggsave(here("figures", "figs11.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs11.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s12

An alluvial plot showing the relationship between the Journal Citation Report Category and heterogeneity assessment

# Data Transformation 
heterogeneity_alluvial <- sd %>% 
    separate_rows(heterogeneity_assessment_method, sep = ",\\s+") %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>% 
  mutate(heterogeneity_assessment_method = ifelse(grepl("not reported", heterogeneity_assessment_method), "no heterogeneity\nmeasure reported", heterogeneity_assessment_method))  %>% 
    filter(!is.na(heterogeneity_assessment_method)) %>%
    group_by(Journal_Category_Allocated_Broad, heterogeneity_assessment_method) %>% 
    count(heterogeneity_assessment_method, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(heterogeneity_assessment_method) 

# Create the Alluvial plot
figs12 <- heterogeneity_alluvial %>% 
ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = heterogeneity_assessment_method)) +
  scale_x_discrete(limits = c("Journal Citation Report Category", "Heterogeneity"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4.5, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()

figs12

  ggsave(here("figures", "figs12.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
  ggsave(here("figures", "figs12.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s13

A bar plot showing the percentage and total count of sensitivity analysis in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple sensitivity analyses are completed

# Calculate the total count for each category
sensitivity_count <- sd %>% 
  separate_rows(sensitivity_analysis_method, sep = ",\\s+") %>% 
  count(sensitivity_analysis_method) %>%
  filter(sensitivity_analysis_method != "NA") %>%   
  group_by(sensitivity_analysis_method) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
sensitivity_pct <- sensitivity_count %>%
  mutate(proportion = n / sum(sensitivity_count$n),
         percentage = proportion * 100)

# Create the count plot
figs13 <- sensitivity_count %>%
  ggplot(aes(x = n, y = reorder(sensitivity_analysis_method, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(sensitivity_analysis_method, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = sensitivity_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(sensitivity_count$n)*1.1)) +
  labs(y = NULL) +
 theme_suppl()

figs13

  ggsave(here("figures", "figs13.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
  ggsave(here("figures", "figs13.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s14

An alluvial plot showing the relationship between the Journal Citation Report Category and sensitivity analysis

# Data Transformation 
sensitivity_analysis_alluvial <- sd %>% 
    separate_rows(sensitivity_analysis_method, sep = ",\\s+") %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>% 
    filter(!is.na(sensitivity_analysis_method)) %>%
    group_by(Journal_Category_Allocated_Broad, sensitivity_analysis_method) %>% 
    count(sensitivity_analysis_method, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(sensitivity_analysis_method)

# Create the Alluvial plot
figs14 <- sensitivity_analysis_alluvial %>% 
ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = sensitivity_analysis_method)) +
  scale_x_discrete(limits = c("Journal Citation Report Category", "Sensitivity Analysis Method"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4.5, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()

figs14

  ggsave(here("figures", "figs14.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
  ggsave(here("figures", "figs14.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s15

A bar plot showing the percentage and total count of bias type assessed in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple bias types are assessed

# Calculate the total count for each category
bias_type_count <- sd %>% 
  separate_rows(bias_assessment_type, sep = ",\\s+") %>% 
  count(bias_assessment_type) %>%
  filter(bias_assessment_type != "NA") %>%
  group_by(bias_assessment_type) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
bias_type_pct <- bias_type_count %>%
  mutate(proportion = n / sum(bias_type_count$n),
         percentage = proportion * 100)

# Create the count plot
figs15 <- bias_type_count %>%
  ggplot(aes(x = n, y = reorder(bias_assessment_type, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(bias_assessment_type, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = bias_type_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(bias_type_count$n)*1.1)) +
  labs(y = NULL) +
  theme_suppl()

figs15

 ggsave(here("figures", "figs15.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs15.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s16

An alluvial plot showing the relationship between the Journal Citation Report Category and bias assessment type

# Data Transformation 
bias_assessment_alluvial <- sd %>% 
    separate_rows(bias_assessment_type, sep = ",\\s+") %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>% 
    filter(!is.na(bias_assessment_type)) %>%
    group_by(Journal_Category_Allocated_Broad, bias_assessment_type) %>% 
    count(bias_assessment_type, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(bias_assessment_type)

# Create the Alluvial plot
figs16 <- bias_assessment_alluvial %>% 
ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = bias_assessment_type)) +
  scale_x_discrete(limits = c("Journal Citation Report Category", "Bias Assessment Type"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()

figs16

 ggsave(here("figures", "figs16.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs16.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s17

A bar plot showing the percentage and total count of bias methodology used in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple bias methodologies are used

# Calculate the total count for each category
bias_method_count <- sd %>% 
  separate_rows(bias_assessment_method, sep = ",\\s+") %>% 
  count(bias_assessment_method) %>%
  filter(bias_assessment_method != "NA") %>%
    group_by(bias_assessment_method) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
bias_method_pct <- bias_method_count %>%
  mutate(proportion = n / sum(bias_method_count$n),
         percentage = proportion * 100)

# Create the count plot
figs17 <- bias_method_count %>%
  ggplot(aes(x = n, y = reorder(bias_assessment_method, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(bias_assessment_method, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = bias_method_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(bias_method_count$n)*1.1)) +
  labs(y = NULL) +
  theme_suppl()

figs17

 ggsave(here("figures", "figs17.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs17.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s18

An alluvial plot showing the relationship between the Journal Citation Report Category and bias assessment method

# Data Transformation 
bias_assessment_alluvial <- sd %>% 
    separate_rows(bias_assessment_method, sep = ",\\s+") %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>% 
    filter(!is.na(bias_assessment_method)) %>%
    group_by(Journal_Category_Allocated_Broad, bias_assessment_method) %>% 
    count(bias_assessment_method, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(bias_assessment_method)

# Create the Alluvial plot
figs18 <- bias_assessment_alluvial %>% 
  ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = bias_assessment_method)) +
  scale_x_discrete(limits = c("Journal Citation Report Category", "Bias Assessment Method"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()

figs18

 ggsave(here("figures", "figs18.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs18.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s19

A bar plot showing the percentage and total count of bias visualizations used in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple bias visualizations are used

# Calculate the total count for each category
bias_visualization_count <- sd %>% 
  separate_rows(bias_assessment_visualization, sep = ",\\s+") %>% 
  count(bias_assessment_visualization) %>%
  filter(bias_assessment_visualization != "NA") %>%
    group_by(bias_assessment_visualization) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
bias_visualization_pct <- bias_visualization_count %>%
  mutate(proportion = n / sum(bias_visualization_count$n),
         percentage = proportion * 100)

# Create the count plot
figs19 <- bias_visualization_count %>%
  ggplot(aes(x = n, y = reorder(bias_assessment_visualization, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(bias_assessment_visualization, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = bias_visualization_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(bias_visualization_count$n)*1.1)) +
  labs(y = NULL) +
 theme_suppl()

figs19

 ggsave(here("figures", "figs19.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs19.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s20

An alluvial plot showing the relationship between the Journal Citation Report Category and bias visualization method

# Data Transformation 
bias_vizualisation_alluvial <- sd %>% 
    separate_rows(bias_assessment_visualization, sep = ",\\s+") %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>% 
    filter(!is.na(bias_assessment_visualization)) %>%
    group_by(Journal_Category_Allocated_Broad, bias_assessment_visualization) %>% 
    count(bias_assessment_visualization, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(bias_assessment_visualization)

# Create the Alluvial plot
figs20 <- bias_vizualisation_alluvial %>% 
  ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = bias_assessment_visualization)) +
  scale_x_discrete(limits = c("Journal Citation Report Category", "Bias Assessment Method"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()

figs20

 ggsave(here("figures", "figs20.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs20.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s21

A bar plot showing the percentage and total count of risk of bias tests used in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple risk of bias tests are used

# Calculate the total count for each category
rob_method_count <- sd %>% 
  separate_rows(rob_assessment_method, sep = ",\\s+") %>% 
  count(rob_assessment_method) %>%
  filter(rob_assessment_method != "NA") %>%
  group_by(rob_assessment_method) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
rob_method_pct <- rob_method_count %>%
  mutate(proportion = n / sum(rob_method_count$n),
         percentage = proportion * 100)

# Create the count plot
figs21 <- rob_method_count %>%
  ggplot(aes(x = n, y = reorder(rob_assessment_method, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(rob_assessment_method, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = rob_method_pct, aes(label = paste0("(", round(percentage, 0), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(rob_method_count$n)*1.1)) +
  labs(y = NULL) +
  theme_suppl()

figs21

 ggsave(here("figures", "figs21.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs21.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s22

An alluvial plot showing the relationship between the Journal Citation Report Category and risk of bias methodology

# Data Transformation 
robmethod_alluvial <- sd %>% 
     separate_rows(rob_assessment_method, sep = ",\\s+") %>%
    filter(!is.na(rob_assessment_method)) %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>%
    group_by(Journal_Category_Allocated_Broad, rob_assessment_method) %>% 
    count(rob_assessment_method, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(rob_assessment_method) 


# Create the Alluvial plot
figs22 <- robmethod_alluvial %>% 
ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = rob_assessment_method)) +
  scale_x_discrete(limits = c("Journal Citation Report Category", "ROB Assessment Method"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()

figs22

 ggsave(here("figures", "figs22.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs22.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s23

A bar plot showing the percentage and total count of visualization methods used in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple visualization methods are used

# Calculate the total count for each category
visualization_count <- sd %>% 
  separate_rows(visualization_method, sep = ",\\s+") %>% 
  count(visualization_method) %>%
  filter(visualization_method != "NA") %>%
    group_by(visualization_method) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
visualization_pct <- visualization_count %>%
  mutate(proportion = n / sum(visualization_count$n),
         percentage = proportion * 100)

# Create the count plot
figs23 <- visualization_count %>%
  ggplot(aes(x = n, y = reorder(visualization_method, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(visualization_method, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = visualization_pct, aes(label = paste0("(", round(percentage, 0), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(visualization_count$n)*1.1)) +
  labs(y = NULL) +
  theme_suppl()

figs23

 ggsave(here("figures", "figs23.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs23.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s24

An alluvial plot showing the relationship between the Journal Citation Report Category and visualization method

# Data Transformation 
vizualization_alluvial <- sd %>% 
    separate_rows(visualization_method, sep = ",\\s+") %>%
    filter(!is.na(visualization_method)) %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>%
    group_by(Journal_Category_Allocated_Broad, visualization_method) %>% 
    count(visualization_method, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(visualization_method) 


# Create the Alluvial plot
figs24 <- vizualization_alluvial %>% 
ggplot(aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = visualization_method)) +
  scale_x_discrete(limits = c("Journal Citation Report Category", "ROB Assessment Method"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  theme_suppl()

figs24

  ggsave(here("figures", "figs24.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
  ggsave(here("figures", "figs24.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s25

A bar plot showing the percentage and total count of reporting guidelines used in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple reporting guidelines are used

# Calculate the total count for each category
reporting_guide_count <- sd %>% 
  separate_rows(reporting_standards_type, sep = ",\\s+") %>% 
  count(reporting_standards_type) %>%
  filter(reporting_standards_type != "NA") %>%
    group_by(reporting_standards_type) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
reporting_guide_pct <- reporting_guide_count %>%
  mutate(proportion = n / sum(reporting_guide_count$n),
         percentage = proportion * 100)

# Create the count plot
figs25 <- reporting_guide_count %>%
  ggplot(aes(x = n, y = reorder(reporting_standards_type, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(reporting_standards_type, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = reporting_guide_pct, aes(label = paste0("(", round(percentage, 0), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(reporting_guide_count$n)*1.1)) +
  labs(y = NULL) +
  theme_suppl()

figs25

 ggsave(here("figures", "figs25.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs25.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s26

An alluvial plot showing the relationship between the Journal Citation Report Category and reporting guideline used

# Data Transformation 
reporting_standards_alluvial <- sd %>% 
    separate_rows(reporting_standards_type, sep = ",\\s+") %>%
    separate_rows(Journal_Category_Allocated_Broad, sep = "/\\s+") %>%
    filter(!grepl("no category found", Journal_Category_Allocated_Broad, ignore.case = TRUE)) %>% 
    filter(!is.na(reporting_standards_type)) %>%
    group_by(Journal_Category_Allocated_Broad, reporting_standards_type) %>% 
    count(reporting_standards_type, Journal_Category_Allocated_Broad) %>% 
    summarise(freq = n(), .groups = 'drop') %>% 
    group_by(reporting_standards_type)


# Create the Alluvial plot
figs26 <- reporting_standards_alluvial %>% 
ggplot( aes(y = freq ,axis1 = Journal_Category_Allocated_Broad, axis2 = reporting_standards_type)) +
  scale_x_discrete(limits = c("Journal Citation Report Category", "Reporting Standards Type"), expand = c(.05, .05)) +
  xlab("Variables") +
  geom_alluvium(aes(fill = Journal_Category_Allocated_Broad)) +
  geom_stratum(width = 1/4, fill = "white", color = "black") +
  labs(x= "Variables", y = "Frequency", fill = "Journal Category Allocated") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 6) +
  theme_suppl()

figs26

 ggsave(here("figures", "figs26.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs26.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure 2

A circular treemap showing the counts of each methodological item in exisitng meta-analysis investigating the impacts of organochlorine pesticides

# Grouping "Medline" and "Pubmed" under "PubMed" and summing the counts
database_count <- database_count %>%
  mutate(database_search = if_else(database_search %in% c("Medline", "Pubmed"), "PubMed", database_search)) %>%
  group_by(database_search) %>%
  summarise(n = sum(n))

# Splitting, grouping, and summing different categories of effect sizes
effectsize_count <- sd %>% 
  separate_rows(effect_size, sep = ",\\s+") %>% 
  count(effect_size) %>%
  filter(effect_size != "NA") %>%
  group_by(effect_size) %>%
  summarise(n = sum(n))

effectsize_count <- effectsize_count %>% 
  mutate(effect_size = if_else(effect_size %in% c("Beta regression coefficient", "Correlation coefficient"), "Correlation", effect_size)) %>% 
  mutate(effect_size = if_else(effect_size %in% c("OR (odds ratio)", "RR (response ratio)", "SMD (standardized mean difference)", "lnPR (log partitioning ratio)", "lnOR (log odds ratio)", "Ratio of means", "InRR (log response ratio)"), "Mean difference", effect_size)) %>% 
  mutate(effect_size = if_else(effect_size %in% c("lnCVR (log coefficient variation ratio)"), "Variation difference", effect_size)) %>% 
  mutate(effect_size = if_else(effect_size %in% c("RR (risk ratio)"), "2x2", effect_size)) %>% 
  mutate(effect_size = if_else(effect_size %in% c("Raw weight", "Transfer rate", "Geometric mean", "Maternal transfer ratio", "SMR (standardized mortality rate)", "Transfer rate", "z-score"), "Other ES", effect_size)) %>% 
  group_by(effect_size) %>%
  summarise(n = sum(n))

# Categorizing software as either "Code-based software" or "GUI" and summing the counts
software_count <- software_count %>%
  mutate(software_analysis = if_else(software_analysis %in% c("Stata", "R"), "Code-based software", software_analysis)) %>%
  mutate(software_analysis = if_else(software_analysis %in% c("CMAS", "Excel", "RevMan", "SAS", "XLSTAT"), "GUI", software_analysis)) %>% 
  group_by(software_analysis) %>%
  summarise(n = sum(n))

# Grouping heterogeneity assessment methods and summing the counts
heterogeneity_count <- heterogeneity_count %>% 
  mutate(heterogeneity_assessment_method = if_else(heterogeneity_assessment_method %in% c("Tau square"), "I square", heterogeneity_assessment_method)) %>% 
  mutate(heterogeneity_assessment_method = if_else(heterogeneity_assessment_method %in% c("Chi square"), "Q statistic", heterogeneity_assessment_method)) %>% 
  mutate(heterogeneity_assessment_method = if_else(heterogeneity_assessment_method %in% c("Galbraith plot", "Baujats plot"), "Plot", heterogeneity_assessment_method)) %>% 
  group_by(heterogeneity_assessment_method) %>%
  summarise(n = sum(n))

# Grouping bias assessment methods with count <= 3 under "Other BA" and summing the counts
bias_method_count <- bias_method_count %>% 
  mutate(bias_assessment_method = ifelse(n<= 3, "Other BA", as.character(bias_assessment_method))) %>% 
  group_by(bias_assessment_method) %>%
  summarise(n = sum(n))

# Grouping sensitivity analysis methods with count <= 3 under "Other SA" and summing the counts
sensitivity_count <-  sensitivity_count %>%  
  mutate(sensitivity_analysis_method = ifelse(n<= 3, "Other SA", as.character(sensitivity_analysis_method))) %>% 
  group_by(sensitivity_analysis_method) %>%
  summarise(n = sum(n))

# Grouping risk of bias assessment methods with count <= 3 under "Other ROB" and summing the counts
rob_method_count <-  rob_method_count %>%  
  mutate(rob_assessment_method = ifelse(n<= 3, "Other ROB", as.character(rob_assessment_method))) %>% 
  group_by(rob_assessment_method) %>%
  summarise(n = sum(n))

# Grouping visualization methods with count <= 3 under "Other Viz" and summing the counts
visualization_count <- visualization_count %>% 
  mutate(visualization_method = ifelse(n<= 3, "Other Viz", as.character(visualization_method))) %>% 
  group_by(visualization_method) %>%
  summarise(n = sum(n))

# Grouping reporting standards types with count <= 2 under "Other guideline" and summing the counts
reporting_guide_count <- reporting_guide_count %>% 
  mutate(reporting_standards_type = ifelse(n<= 2, "Other guideline", as.character(reporting_standards_type))) %>% 
  group_by(reporting_standards_type) %>%
  summarise(n = sum(n))

# Grouping bias assessment visualization types and summing the counts
bias_visualization_count <- bias_visualization_count %>% 
  mutate(bias_assessment_visualization = if_else(bias_assessment_visualization %in% c("doi plot", "trim and fill", "Funnel plot"), "Bias visualization", bias_assessment_visualization)) %>% 
  group_by(bias_assessment_visualization) %>%
  summarise(n = sum(n))

# Combine the data frames and unite the methodology types
df <- bind_rows(
  database_count %>% mutate(methodology_type = 'Database Search'),
  effectsize_count %>% mutate(methodology_type = 'Effect Size'),
  software_count %>%  mutate(methodology_type = "Software"),
  heterogeneity_count %>% mutate(methodology_type = "Heterogeneity"),
  sensitivity_count %>% mutate(methodology_type = "Sensitivity_Analysis"),
  bias_method_count %>%  mutate(methodology_type = "Bias Assessment"),
  rob_method_count %>% mutate(methodology_type = "Risk  of Bias"), 
 # visualization_count %>% mutate(methodology_type = "Visualization"),
  reporting_guide_count %>%  mutate(methodology_type = "Reporting Guide"),
  bias_visualization_count %>%  mutate(methodology_type = "Bias Assessment")
) %>% 
 unite(methodology_type_specific, 
       database_search, 
       effect_size,  
       software_analysis,
       heterogeneity_assessment_method, 
       sensitivity_analysis_method, 
       bias_assessment_method,
       rob_assessment_method, 
      # visualization_method, 
       reporting_standards_type, 
       bias_assessment_visualization,
       remove = TRUE, na.rm = TRUE)



# Preparing the edges dataframe for creating the graph
edges <- df %>%
  rename(from = methodology_type, to = methodology_type_specific, size = n) %>%
  select(c(from,to,size)) %>%
  as.data.frame()

# Preparing the vertices dataframe for creating the graph
vertices <- df  %>%
  rename(name = methodology_type_specific, size = n) %>%
  select(c(name,size)) %>%
  as.data.frame()

# Appending unique 'from' values to vertices and their corresponding summed sizes
vertices[(nrow(edges)+1):(nrow(edges)+length(unique(edges$from))),1] <- unique(edges$from)
N <- aggregate(edges$size, list(edges$from), FUN=sum)
vertices[(nrow(edges)+1):(nrow(edges)+length(unique(edges$from))),2] <- N$x

# Creating a graph object from the edges and vertices dataframes
mygraph <- graph_from_data_frame(edges, vertices = vertices)

# Plotting the graph using a 'circlepack' layout, adding labels and adjusting aesthetics
fig2 <- ggraph(mygraph, layout = 'circlepack', weight = size) + 
    geom_node_circle(aes(fill = as.factor(depth)), color = NA, alpha = 0.5) +
    geom_node_text(aes(label = name, filter = leaf, size = 2), vjust = -0.3, fontface = "bold") +
    geom_node_text(aes(label = paste0("(", size, ")"), filter = leaf, size = 2), vjust = 1, fontface = "bold") +
    theme_void() +
    theme(legend.position = "none") +
    scale_fill_manual(values = c("#1b9e77", "#E7298A"))


fig2

ggsave(here("figures", "fig2.pdf"), width = 21, height = 15, units = "cm", scale = 2, dpi = 800)
ggsave(here("figures", "fig2.jpg"), width = 21, height = 15, units = "cm", scale = 2, dpi = 800)

Figure 3

The average reporting quality and rigour of meta-analysis according to CEESAT 2.1 (Woodcock et al., 2014). Gold is regard as the highest score, green is second highest score, amber is second-lowest score, and red is the lowest score. All CEESAT 2.1 items along with our interpretation are provided in the supplementary file x.

# Start the data manipulation
percent_ceesat_score <- sd %>%
  filter(!is.na(author_year)) %>%
  select(studies = author_year, starts_with("CEE")) %>%
  na.omit() %>%
  pivot_longer(cols = -studies, names_to = "question", values_to = "score") %>%
  group_by(question, score) %>%
  summarise(n = n(), .groups = 'drop') %>%
  mutate(percent = (n/sum(n))*100, 
         across(c(question, score), as.factor),
         question = fct_recode(question, 
           `1.1 Are the elements of the review question clear?` = "CEESAT2_1.1",
           `2.1 Is there an a-priori method protocol document?` = "CEESAT2_2.1",
           `3.1. Is the approach to searching clearly definedsystematic and\ntransparent?` = "CEESAT2_3.1",
           `3.2. Is the search comprehensive?` = "CEESAT2_3.2",
           `4.1. Are eligibility criteria clearly defined?` = "CEESAT2_4.1",
           `4.2. Are eligibility criteria consistently applied to all potentially relevant\narticles and studies found during the search?` = "CEESAT2_4.2",
           `4.3. Are eligibility decisions transparently reported?` = "CEESAT2_4.3",
           `5.1. Does the review critically appraise each study?` = "CEESAT2_5.1",
           `5.2. During critical appraisal was an effort made to minimise\nsubjectivity?` = "CEESAT2_5.2",
           `6.1. Is the method of data extraction fully documented?` = "CEESAT2_6.1",
           `6.2. Are the extracted data reported for each study?` = "CEESAT2_6.2",
           `6.3. Were extracted data cross checked by more than one reviewer?` = "CEESAT2_6.3",
           `7.1. Is the choice of synthesis approach appropriate?` = "CEESAT2_7.1",
           `7.2. Is a statistical estimate of pooled effect provided together with\nmeasure of variance and heterogeneity among studies?` = "CEESAT2_7.2",
           `7.3 Is variability in the study findings investigated and discussed?` = "CEESAT2_7.3",
           `8.1 Have the authors considered limitations in the synthesis?` = "CEESAT2_8.1"),
         question = factor(question, levels = rev(levels(question))),
         score = factor(score, levels = levels(score)[c(4,1,3,2)]))




fig3 <- ggplot(data = percent_ceesat_score, aes(x = question, y = percent, fill = score)) +
  geom_col(width = 0.7, position = "fill", color = "black") +
  geom_text(aes(label = n), position = position_fill(vjust = 0.5), size = 7, fontface = "bold") +
  coord_flip() +
  guides(fill = guide_legend(reverse = TRUE)) +
  scale_fill_manual(values = c("#FF0000","#FFD700","#008000", "#DAA520"), name = "Score:") +
  scale_y_continuous(labels = scales::percent) +
  theme(panel.grid.major = element_blank(), 
        panel.grid.minor = element_blank(), 
        panel.background = element_blank(),
        axis.text.y = element_text(size = 20),
        axis.text.x = element_text(size = 20),
        axis.title.x = element_text(size = 25),
        axis.title.y = element_text(size = 25), 
          legend.position = "none") +
  ylab("Percentage") + 
  xlab("CEESAT Question")



ggsave(here("figures", "fig3.pdf"), width = 25, height = 15, units = "cm", scale = 2, dpi = 800)
ggsave(here("figures", "fig3.jpg"), width = 25, height = 15, units = "cm", scale = 2, dpi = 800)

Objective 2

To explore the various characteristics of the organochlorine pesticides literature such as the pesticides used, the impacts elicited in response and the subjects that were investigated.

Figure s27

A bar plot showing the percentage and total count of total of pesticides investigate in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple organochlorine pesticides. Filtered for pesticide counts greater than 6.

# Function to replace long OCP names with abbreviations
replace_ocp <- function(df) {
  df %>% 
    mutate(ocp = case_when(
      # HCH related replacements
      grepl("Hexachlorocyclohexane \\(HCH\\)", ocp, ignore.case = TRUE) ~ "HCH",
      grepl("alpha-Hexachlorocyclohexane \\(alpha-HCH\\)", ocp, ignore.case = TRUE) ~ "α - HCH",
      grepl("beta-Hexachlorocyclohexane \\(beta-HCH\\)", ocp, ignore.case = TRUE) ~ "β - HCH",
      grepl("gamma-Hexachlorocyclohexane \\(gamma-HCH\\)", ocp, ignore.case = TRUE) ~ "Lindane",
      # DDT related replacements
      grepl("Dichlorodiphenyltrichloroethane \\(DDT\\)", ocp, ignore.case = TRUE) ~ "DDT",
      grepl("p,p-Dichlorodiphenyltrichloroethane \\(p,p-DDT\\)", ocp, ignore.case = TRUE) ~ "p,p-DDT",
      grepl("o,p-Dichlorodiphenyltrichloroethane \\(o,p-DDT\\)", ocp, ignore.case = TRUE) ~ "o,p-DDT",
      # DDD related replacements
      grepl("Dichlorodiphenyldichloroethane \\(DDD\\)", ocp, ignore.case = TRUE) ~ "DDD",
      grepl("p,p-Dichlorodiphenyldichloroethane \\(p,p-DDD\\)", ocp, ignore.case = TRUE) ~ "p,p-DDD",
      grepl("o,p-Dichlorodiphenyldichloroethane \\(o,p-DDD\\)", ocp, ignore.case = TRUE) ~ "o,p-DDD",
      # DDE related replacements
      grepl("Dichlorodiphenyldichloroethylene \\(DDE\\)", ocp, ignore.case = TRUE) ~ "DDE",
      grepl("p,p-Dichlorodiphenyldichloroethylene \\(p,p-DDE\\)", ocp, ignore.case = TRUE) ~ "p,p-DDE",
      grepl("o,p-Dichlorodiphenyldichloroethylene \\(o,p-DDE\\)", ocp, ignore.case = TRUE) ~ "o,p-DDE",
      TRUE ~ ocp  # no change for any others
    ))
}
# Transform the data 
ocp_count <-
  ocp %>% 
  separate_rows(ocp, sep = ",\\s+") %>% 
  replace_ocp %>% 
  count(ocp) %>% 
  filter(!is.na(ocp)) %>% # filter out NA 
  arrange(desc(n)) %>% 
  mutate(ocp = ifelse(n <= 6, "other OCP", as.character(ocp))) %>% 
# Other organochlorine pesticides include: toxaphene (n=6), Methoxychlor (n=6), p,p-DDD (n=5), o,p-DDD (n=5), cis-Chlordane (n=5), trans=Chlordane (n=4), Endosulfan II (n=4), Endosulfan (n=3),o,p-DDD (n=3), cis-Nonachlor (n=3) y-Chlordane (n=2), Chlorophenol (n=2), beta-BHC (n=2), alpha-Chlordane (n=2), TCDD (n=1), Nonachlore (n=1), Endrin ketone (n=1), Endrin Aldehyde (n=1), Endosulfan sulfate (n=1), Dicofol (n=1), delta-HCH (n=1), delta-BHC (n=1), DDD (n=1), cis-Heptachlor (n=1), alpha-BHC (n=1).
  group_by(ocp) %>% 
  summarise(n =sum(n))

# Calculate the proportion and percentage of each OCP
ocp_pct <- ocp_count %>%
  mutate(proportion = n/sum(ocp_count$n),
         percentage = proportion*100)

# Create the count plot for OCPs
figs27 <- ocp_count %>%
  ggplot(aes(x = n, y = reorder(ocp, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8, alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(ocp, n)), hjust = 0.5, size = 6, color = "black") +
  geom_text(data = ocp_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = - 0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(ocp_count$n)*1.2)) +
  labs(y = NULL) +
  theme_minimal() +
  theme(axis.text.y = element_text(size = 15),
        axis.text.x = element_text(size = 15),
        axis.line.x = element_line(color = "gray", size = 0.5),
        axis.line.y = element_blank(),
        axis.ticks.x = element_blank(),
        axis.ticks.y = element_blank(),
        axis.title.x = element_text(size = 20),
        axis.title.y = element_text(size = 20),
        panel.grid.major.y = element_blank(),
        panel.grid.minor.y = element_blank(),
        legend.position = "none"
        )
figs27

  ggsave(here("figures", "figs27.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
  ggsave(here("figures", "figs27.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s28

A bar plot showing the percentage and total count of total of subjects investigate in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple subjects

# Calculate total count for each category
subject_count <- 
  sub %>% 
    separate_rows(subject, sep = ",\\s+") %>% 
    count(subject)

# Calculate proportion and percentage for each category
subject_pct <- subject_count %>%
  mutate(proportion = n/sum(subject_count$n),
         percentage = proportion*100)

# Create the count plot for subjects
figs28 <- subject_count %>%
  ggplot(aes(x = n, y = reorder(subject, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(subject, n)), hjust = 0.5, size = 7, color = "black") +
  geom_text(data = subject_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(subject_count$n)*1.1)) +
  labs(y = NULL) +
  theme_minimal() +
  theme(axis.text.y = element_text(size = 15),
        axis.text.x = element_text(size = 15),
        axis.line.x = element_line(color = "gray", size = 0.5),
        axis.line.y = element_blank(),
        axis.ticks.x = element_blank(),
        axis.ticks.y = element_blank(),
        axis.title.x = element_text(size = 20),
        axis.title.y = element_text(size = 20),
        panel.grid.major.y = element_blank(),
        panel.grid.minor.y = element_blank(),
        legend.position = "none"
        )

figs28

 ggsave(here("figures", "figs28.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
 ggsave(here("figures", "figs28.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s29

A bar plot showing the percentage and total count of total of subjects investigate in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple subjects. Filtered for impact counts greater than 1.

# Calculate total count for each category
impact_count <- 
  im %>% 
    separate_rows(impact, sep = ",\\s+") %>% 
    count(impact) %>% 
  filter(impact != "NA") %>%
  mutate(impact = ifelse(n<= 1, "other", as.character(impact))) %>% 
    group_by(impact) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
impact_pct <- impact_count %>%
  mutate(proportion = n/sum(impact_count$n),
         percentage = proportion*100)

# Create the count plot for impacts 
figs29 <- impact_count %>%
  ggplot(aes(x = n, y = reorder(impact, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(impact, n)), hjust = 0.5, size = 7, color = "black") +
  geom_text(data = impact_pct, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(impact_count$n)*1.1)) +
  labs(y = NULL) +
  theme_minimal() +
  theme(axis.text.y = element_text(size = 15),
        axis.text.x = element_text(size = 15),
        axis.line.x = element_line(color = "gray", size = 0.5),
        axis.line.y = element_blank(),
        axis.ticks.x = element_blank(),
        axis.ticks.y = element_blank(),
        axis.title.x = element_text(size = 20),
        axis.title.y = element_text(size = 20),
        panel.grid.major.y = element_blank(),
        panel.grid.minor.y = element_blank(),
        legend.position = "none"
        )

figs29

  ggsave(here("figures", "figs29.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
  ggsave(here("figures", "figs29.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s30

A bar plot showing the percentage and total count of total of impact categories investigated in meta-analysis investigating the impacts of organochlorine pesticides. Note: some meta-analysis may contribute to multiple sections if the study involves multiple impacts

# Create a collumn for broad impacts
im <- im %>%
        separate_rows(impact, sep = ",\\s+") %>% 
  mutate(impact_broad = case_when(
    impact %in% c("parkinsons disease", "alzheimers disease", "autism spectrum disorder", "brain tumour", "amyotrophic lateral sclerosis" ) ~ "Neurological",
    impact %in% c("concentration", "contamination") ~ "Concentration",
    impact %in% c("diabetes", "thyroid function", "hypertension", "endometriosis") ~ "Endocrine",
    grepl("cancer", impact, ignore.case = TRUE) | impact %in% c("leukemia", "lymphoma", "multiple myeloma", "neuroblastoma") ~ "Carcinogen",
    impact %in% c("respiratory health", "cardiovascular disease", "asthma", "prolonged bradycardia") ~ "Cardiovascular",
 #   impact %in% c("birth outcomes", "birth weight", "preterm birth") ~ "Birth",
    impact %in% c("obesity", "adiposity") ~ "Obesity",
    impact %in% c("sperm quality", "neuroblastoma", "hypospadias", "cryptochidism", "reproductive system") ~ "Reproduction",
    TRUE ~ "Other Impact"
  ))


# Calculate total count for each category
impact_count_broad <- 
  im %>% 
    separate_rows(impact_broad, sep = ",\\s+") %>% 
    count(impact_broad) %>% 
  filter(impact_broad != "NA") %>%
    group_by(impact_broad) %>%
  summarise(n = sum(n))

# Calculate proportion and percentage for each category
impact_pct_broad <- impact_count_broad %>%
  mutate(proportion = n/sum(impact_count_broad$n),
         percentage = proportion*100)


# Create the count plot for impacts 
figs30 <- impact_count_broad %>%
  ggplot(aes(x = n, y = reorder(impact_broad, n), fill = "#1b9e77")) +
  geom_bar(stat = "identity", width = 0.8 , alpha = 0.7) +
  geom_text(aes(label = n, x = n / 2, y = reorder(impact_broad, n)), hjust = 0.5, size = 7, color = "black") +
  geom_text(data = impact_pct_broad, aes(label = paste0("(", round(percentage, 1), "%)"), x = n), 
            hjust = -0.1, size = 6, color = "black", fontface = "bold") +
  scale_fill_identity(guide = "none") +
  scale_x_continuous(name = "Article Count", expand = c(0, 0), limits = c(0, max(impact_count_broad$n)*1.1)) +
  labs(y = NULL) +
  theme_minimal() +
  theme(axis.text.y = element_text(size = 15),
        axis.text.x = element_text(size = 15),
        axis.line.x = element_line(color = "gray", size = 0.5),
        axis.line.y = element_blank(),
        axis.ticks.x = element_blank(),
        axis.ticks.y = element_blank(),
        axis.title.x = element_text(size = 20),
        axis.title.y = element_text(size = 20),
        panel.grid.major.y = element_blank(),
        panel.grid.minor.y = element_blank(),
        legend.position = "none"
        )

figs30

   ggsave(here("figures", "figs30.pdf"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)
   ggsave(here("figures", "figs30.jpg"), width = 16, height = 10, units = "cm", scale = 2, dpi = 800)

Figure s31

An alluvial plot showing the relationships between the pesticide of exposure, the subject being exposed and the impact of exposure

# Function to change OCP to be more general
replace_ocp2 <- function(df) {
  df %>% 
  mutate(ocp = case_when(
    grepl("Chlordane", ocp, ignore.case = TRUE) ~ "Chlordane",  
    grepl("Endosulfan", ocp, ignore.case = TRUE) ~ "Endosulfan", 
    grepl("Nonachlor", ocp, ignore.case = TRUE) ~ "Nonachlore", 
    grepl("Heptachlor", ocp, ignore.case = TRUE) ~ "Heptachlor",
    grepl("TCDD", ocp, ignore.case = TRUE) ~ "TCDD", 
    grepl("Endrin", ocp, ignore.case = TRUE) ~ "Endrin",
    grepl("Hexachlorobenzene", ocp, ignore.case = TRUE) ~ "HCH",
    grepl("Lindane", ocp, ignore.case = TRUE) ~ "HCH", 
    grepl("Hexachlorocyclohexane \\(HCH\\)", ocp, ignore.case = TRUE) ~ "HCH",
    grepl("alpha-Hexachlorocyclohexane \\(alpha-HCH\\)", ocp, ignore.case = TRUE) ~ "HCH",
    grepl("beta-Hexachlorocyclohexane \\(beta-HCH\\)", ocp, ignore.case = TRUE) ~ "HCH",
    grepl("gamma-Hexachlorocyclohexane \\(gamma-HCH\\)", ocp, ignore.case = TRUE) ~ "HCH",
    grepl("Dichlorodiphenyltrichloroethane \\(DDT\\)", ocp, ignore.case = TRUE) ~ "DDT",
    grepl("p,p-Dichlorodiphenyltrichloroethane \\(p,p-DDT\\)", ocp, ignore.case = TRUE) ~ "DDT",
    grepl("o,p-Dichlorodiphenyltrichloroethane \\(o,p-DDT\\)", ocp, ignore.case = TRUE) ~ "DDT",
    grepl("Dichlorodiphenyldichloroethane \\(DDD\\)", ocp, ignore.case = TRUE) ~ "DDD",
    grepl("p,p-Dichlorodiphenyldichloroethane \\(p,p-DDD\\)", ocp, ignore.case = TRUE) ~ "DDD",
    grepl("o,p-Dichlorodiphenyldichloroethane \\(o,p-DDD\\)", ocp, ignore.case = TRUE) ~ "DDD",
    grepl("Dichlorodiphenyldichloroethylene \\(DDE\\)", ocp, ignore.case = TRUE) ~ "DDE",
    grepl("p,p-Dichlorodiphenyldichloroethylene \\(p,p-DDE\\)", ocp, ignore.case = TRUE) ~ "DDE",
    grepl("o,p-Dichlorodiphenyldichloroethylene \\(o,p-DDE\\)", ocp, ignore.case = TRUE) ~ "DDE",
    TRUE ~ ocp
  ))
}
 

# Transform the data 
alluvial <- im %>%
  left_join(ocp, by = "study_id") %>%
  left_join(sub, by = "study_id") %>%
  separate_rows(subject, sep = ",\\s+") %>% 
  separate_rows(ocp, sep = ",\\s+") %>% 
  separate_rows(impact_broad, sep = ",\\s+") %>%
  replace_ocp2() %>%
  filter(!grepl("not reported", ocp, ignore.case = TRUE)) %>%
  group_by(ocp, subject, impact_broad) %>%
  summarise(freq = n(), .groups = 'drop') %>%
  group_by(ocp) %>%
  filter(sum(freq) > 10) %>%  
  group_by(impact_broad) %>% 
  filter(sum(freq) > 5) %>% 
  mutate(subject = factor(subject, levels = c("Environment", "Non-human animal", "Human"), ordered = TRUE))


figs31 <- alluvial %>% 
  ggplot(
       aes(axis1 = ocp, axis2 = subject, axis3 = impact_broad, y = freq)) +
  scale_x_discrete(limits = c("Organochlorine Pesticide", "Subject", "Impact"), expand = c(.05, .10)) +
  xlab("Variables") +
  ylab("Frequency") +  
  geom_alluvium(aes(fill = subject)) +
  geom_stratum(width = 1/2, fill = "white", color = "black") +
  geom_text(stat = "stratum", aes(label = after_stat(stratum)), size = 5, fontface = "bold") +  
  theme_minimal() +
  theme(axis.text=element_text(size=15),  
        axis.title=element_text(size=20),
        legend.position="none",
        panel.grid.major = element_blank(),  
        panel.grid.minor = element_blank()  
  ) + 
  scale_fill_brewer(palette = "Dark2", name = "Subject Category")

figs31

    ggsave(here("figures", "figs31.pdf"), width =18, height = 12, units = "cm", scale = 2, dpi = 800)
    ggsave(here("figures", "figs31.jpg"), width = 18, height = 12, units = "cm", scale = 2, dpi = 800)

Figure

# Join the organochlorine pesticide details with the impact details
ocp_im <- left_join(ocp, im ,sub, by = "study_id") 

# Separate rows in "ocp_im"
ocp_im1 <- separate_rows(ocp_im, ocp , sep = ", ", convert = TRUE)


# Group by "ocp" and "impact" and summarize count
ocp_im_summary <- ocp_im1 %>%
  mutate(ocp = str_trim(ocp),
         impact_broad = str_trim(impact_broad)) %>%
    replace_ocp2() %>% 
  group_by(ocp, impact_broad) %>%
  summarise(count = n(), .groups = "drop") 


# Filter for top 5 pesticides 
top_pesticides <- ocp_im_summary %>%
  filter(ocp != "not reported") %>%
  group_by(ocp) %>%
  summarise(total_count = sum(count)) %>%
  top_n(8, total_count) %>%
  pull(ocp) 


ocp_im_summary_filtered <- ocp_im_summary %>%
  filter(ocp %in% top_pesticides)

# Create a circle plot with impact on the x-axis and ocp on the y-axis
ocp_im_summary_filtered %>% 
ggplot(aes(x = fct_rev(fct_reorder(impact_broad, count, .fun = 'sum')),
           y = fct_reorder(ocp, count, .fun = 'sum'),
           size = count,
           fill = count)) +
  geom_point(shape = 21, color = "white") +
  geom_text(aes(label = count), size = 8, fontface = "bold") +  
  scale_fill_gradient(low = "#98FB98", high = "#006400") +
  labs(x = "Impact",
       y = "Organochlorine Pesticide",
       fill = "Count") +
  theme_minimal() +
  theme(
        axis.ticks.y = element_blank(),
        axis.text.x = element_text(size = 20),  
        axis.text.y = element_text(size = 20, hjust = 1),  
        axis.title.x = element_text(size = 25),  
        axis.title.y = element_text(size = 25),  
        legend.position = "none") +
  scale_size_continuous(range = c(15, 45)) 

  ggsave(here("figures", "fig3.pdf"), width = 25, height = 15, units = "cm", scale = 2, dpi = 800)
  ggsave(here("figures", "fig3.jpg"), width = 25, height = 15, units = "cm", scale = 2, dpi = 800)
  • Objective 4. Bibliometrics: How is synthesized organochlorine pesticide evidence connected? We will investigate the countries and institutions that are primarily engaged in secondary research on organochlorine pesticides, and analyze the networks that exist between them. By doing so, we hope to gain insights into the collaborative relationships between different institutions and identify any patterns or trends in the distribution of research efforts.
fig5a <- biblioAnalysis(bib_sco)
plot(fig5a)

fig5c - thematic map based on keywords

par(mfrow=c(1,1), mar=c(0,2,0,2))
fig5c <- thematicMap(bib_sco, field = "ID", n = 1000, minfreq = 5, stemming = FALSE, size = 0.5, n.labels = 1, repel = TRUE)
plot(fig5c$map)

fig 5d - author collaboration network

NetMatrix_authors <- biblioNetwork(bib_sco, analysis = "collaboration",  network = "authors", sep = ";")
fig5d <- networkPlot(NetMatrix_authors,  n = 100, 
                                      Title = "Author collaboration", 
                                      type = "auto", size = 4, size.cex = TRUE, 
                                      edgesize = 10, labelsize = 1.1)

fig5e - country publications map

# Extract country information from the "AU1_CO" and "AU_CO" fields of the "bib_sco" dataset
bibmap <- metaTagExtraction(bib_sco, Field = "AU1_CO", sep = ";") 
bibmap <- metaTagExtraction(bibmap, Field = "AU_CO", sep = ";") 

# Create a data frame with counts of articles from each country
firstcountrycounts <- bibmap %>% 
  group_by(AU1_CO) %>% 
  count() %>% 
  filter(!is.na(AU1_CO))  

# Load world map data and remove countries with longitude >180 to make an equal projection-like map
world_map <- map_data("world") %>% 
  filter(! long > 180)

# Format country names to match regions on the world map
firstcountrycounts$region <- str_to_title(firstcountrycounts$AU1_CO)
firstcountrycounts$region[firstcountrycounts$region == "Usa"] <- "USA" 
firstcountrycounts$region[firstcountrycounts$region == "Korea"] <- "South Korea"

# Join count data with map data and set missing counts to zero
emptymap <- tibble(region = unique(world_map$region), n = rep(0,length(unique(world_map$region))))
fullmap <- left_join(emptymap, firstcountrycounts, by = "region")
fullmap$n <- fullmap$n.x + fullmap$n.y
fullmap$n[is.na(fullmap$n)] <- 0

fig5 <- fullmap %>%
  ggplot(aes(fill = n, map_id = region)) +
  geom_map(map = world_map, color = "gray50") +
  expand_limits(x = world_map$long, y = world_map$lat) +
  coord_map("mercator") +
  theme_minimal() +
  theme(
    axis.text = element_blank(),  
    axis.title = element_blank(),  
    legend.position = "bottom",
    legend.box = "horizontal",  
    legend.box.just = "center",  
    legend.margin = margin(t = 10, unit = "pt"),  
    legend.text = element_text(size = 12),  
    legend.title = element_text(size = 14, face = "bold"),  
    legend.key.width = unit(30, "mm")  
  ) +
  scale_fill_gradient(
    low = "#98FB98", high = "#006400",
    name = "Score", na.value = "gray70",
    limits = c(1, 20)) +
  guides(
    fill = guide_colourbar(
      barwidth = unit(180, units = "mm"),
      barheight = unit(3, units = "mm")
    )
  )

fig5

# ggsave(here("figures", "fig5.pdf"), width = 21, height = 12, units = "cm", scale = 2, dpi = 800)
# ggsave(here("figures", "fig5.jpg"), width = 21, height = 12, units = "cm", scale = 2, dpi = 800)

Map of europe

fig5f <- fullmap %>%
ggplot(aes(fill = n, map_id = region)) +
geom_map(map = world_map, color = "gray50") +
coord_map("mercator", ylim = c(30, 65), xlim = c(-25, 45)) + # set limits for Europe
theme(legend.position = "right") +
scale_fill_gradient(low = "#98FB98", high = "#006400",
name = "Score", na.value = "gray70",
limits = c(1, 10),
guide = guide_colorbar(direction = "vertical.")) +
guides(fill = guide_colourbar(barwidth = unit(10, units = "mm"), barheight = unit(20, units = "mm"))) +
theme(axis.text.x = element_blank(),
axis.text.y = element_blank(),
axis.title.x = element_blank(),
axis.title.y = element_blank(),
panel.grid.major = element_blank(),
panel.grid.minor = element_blank(),
panel.background = element_blank())

fig5f

fig5f - country collaboration network circle plot

# Extract countries from the affiliations
bib_sco2 <- metaTagExtraction(bib_sco, Field = "AU_CO", sep = ";")

# Create a network matrix of collaborations between countries
NetMatrix_country <- biblioNetwork(bib_sco2, analysis = "collaboration", network = "countries", sep = ";")

# Convert the network matrix to a standard matrix
NetMatrix_country <- as.matrix(NetMatrix_country)

# Remove the lower triangle (as this is duplication of info)
NetMatrix_country[lower.tri(NetMatrix_country)] <- 0 

# Change column and row names to title case
colnames(NetMatrix_country) <- str_to_title(colnames(NetMatrix_country))
rownames(NetMatrix_country) <- str_to_title(rownames(NetMatrix_country))

# Change "Usa" to "USA"
colnames(NetMatrix_country)[colnames(NetMatrix_country) == "Usa"] <- "USA"
rownames(NetMatrix_country)[rownames(NetMatrix_country) == "Usa"] <- "USA"

# Change "United Kingdom" to "UK" for easier plotting
colnames(NetMatrix_country)[colnames(NetMatrix_country) == "United Kingdom"] <- "UK"
rownames(NetMatrix_country)[rownames(NetMatrix_country) == "United Kingdom"] <- "UK"

# Define colors for each country
my.cols2 <- c(
  USA = "#377eb8",
  Spain = "#ffff33",
  China = "#e41a1c",
  France = "#999999",
  Canada = "#a6cee3",
  Denmark = "#b2df8a",
  Netherlands = "#377eb8",
  Belgium = "#984ea3",
  UK = "#ffff33",
  Australia = "#4daf4a",
  Brazil = "#4daf4a",
  Germany = "#b2df8a",
  Greece = "#f781bf",
  Korea = "#f781bf",
  Ireland = "#a65628",
  Norway = "#ff7f00",
  Sweden = "#4daf4a",
  Egypt = "#f781bf",
  Italy = "#e41a1c",
  Japan = "#1f78b4",
  Switzerland = "#984ea3",
  Turkey = "#33a02c",
  Austria = "#b2df8a",
  Israel = "#f781bf",
  NewZealand = "#4daf4a",
  Russia = "#999999",
  Singapore = "#b2df8a",
  Portugal = "#984ea3",
  Finland = "#b2df8a",
  Mexico = "#a65628",
  Poland = "#b2df8a",
  SouthAfrica = "#f781bf",
  Argentina = "#ff7f00",
  Chile = "#ff7f00",
  CzechRepublic = "#b2df8a",
  Iceland = "#b2df8a",
  Peru = "#ff7f00",
  Romania = "#fb9a99",
  Serbia = "#fb9a99",
  UAE = "#a65628"
)

# Setting up custom parameters
circos.par(cell.padding = c(0, 0, 0, 0), track.margin = c(0, 0))

# Create a chord diagram of the network matrix
fig5f <- chordDiagram(NetMatrix_country, annotationTrack = "grid", preAllocateTracks = 1, grid.col = my.cols2)

# Add a track to label each sector with its name
circos.trackPlotRegion(track.index = 1, bg.border = NA, panel.fun = function(x, y) {
  xlim = get.cell.meta.data("xlim")
  ylim = get.cell.meta.data("ylim")
  sector.name = get.cell.meta.data("sector.index")
  circos.text(mean(xlim), ylim[1] + 0.2 , sector.name, facing = "clockwise", niceFacing = TRUE, adj = c(0, 0))
  circos.axis(h = "top", labels.cex = 0.5, major.tick.length = 0.2, sector.index = sector.name, track.index = 2)
})

fig5g collaboration matrix with self citation removed

diag(NetMatrix_country) <- 0

# Create a chord diagram of the network matrix
fig5g <- chordDiagram(NetMatrix_country, annotationTrack = "grid", preAllocateTracks = 1, grid.col = my.cols2)

# Add a track to label each sector with its name
circos.trackPlotRegion(track.index = 1, panel.fun = function(x, y) {
  xlim = get.cell.meta.data("xlim")
  ylim = get.cell.meta.data("ylim")
  sector.name = get.cell.meta.data("sector.index")
  circos.text(mean(xlim), ylim[1] + 0.2, sector.name, facing = "clockwise", niceFacing = TRUE, adj = c(0, 0.5))
  circos.axis(h = "top", labels.cex = 0.5, major.tick.length = 0.2, sector.index = sector.name, track.index = 2)
}, bg.border = NA)

fig 5h contitnent collaboration

NetMatrix_continent <- NetMatrix_country
colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "USA"] <- "North America"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "USA"] <- "North America"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Spain"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Spain"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "China"] <- "Asia"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "China"] <- "Asia"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "France"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "France"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Canada"] <- "North America"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Canada"] <- "North America"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Denmark"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Denmark"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Netherlands"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Netherlands"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Belgium"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Belgium"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "UK"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "UK"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Australia"] <- "Australia"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Australia"] <- "Australia"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Brazil"] <- "South America"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Brazil"] <- "South America"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Germany"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Germany"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Finland"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Finland"] <- "Europe"


colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Greece"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Greece"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Korea"] <- "Asia"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Korea"] <- "Asia"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Norway"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Norway"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Sweden"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Sweden"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Egypt"] <- "Africa"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Egypt"] <- "Africa"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Italy"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Italy"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Japan"] <- "Asia"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Japan"] <- "Asia"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Portugal"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Portugal"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Switzerland"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Switzerland"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Turkey"] <- "Asia"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Turkey"] <- "Asia"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "India"] <- "Asia"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "India"] <- "Asia"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Iran"] <- "Asia"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Iran"] <- "Asia"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Costa Rica"] <- "North America"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Costa Rica"] <- "North America"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Czech Republic"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Czech Republic"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Hong Kong"] <- "Asia"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Hong Kong"] <- "Asia"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Iceland"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Iceland"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Ireland"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Ireland"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Mexico"] <- "North America"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Mexico"] <- "North America"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Romania"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Romania"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Slovakia"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Slovakia"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Ukraine"] <- "Europe"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Ukraine"] <- "Europe"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Australia"] <- "Oceania"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Australia"] <- "Oceania"

colnames(NetMatrix_continent)[colnames(NetMatrix_continent) == "Kazakhstan"] <- "Asia"
rownames(NetMatrix_continent)[rownames(NetMatrix_continent) == "Kazakhstan"] <- "Asia"


# collapsing
merge_matrix <- t(rowsum(t(NetMatrix_continent), group = colnames(NetMatrix_continent), na.rm = T))
merge_matrix2 <- rowsum(merge_matrix, group = rownames(merge_matrix))
# remove diagonal elements
diag(merge_matrix2) <- 0
# chord plot
chordDiagramFromMatrix(merge_matrix2)

# Define colors for each continent
my.cols2 <- c(
  Africa = "#CC79A7",
  NorthAmerica = "#F0E442",
  Asia = "#0072B2",
  Europe = "#E69F00",
  Oceania = "#009E73",
  SouthAmerica = "#D55E00"
)


# Create a chord diagram of the network matrix
fig5h <- chordDiagram(merge_matrix2, annotationTrack = "grid", preAllocateTracks = 1)
# Add a track to label each sector with its name
circos.trackPlotRegion(track.index = 1, panel.fun = function(x, y) {
  xlim = get.cell.meta.data("xlim")
  ylim = get.cell.meta.data("ylim")
  sector.name = get.cell.meta.data("sector.index")
  circos.text(mean(xlim), ylim[1] + 0.2, sector.name, facing = "clockwise", niceFacing = TRUE, adj = c(0, 0.5))
  circos.axis(h = "top", labels.cex = 0.5, major.tick.length = 0.2, sector.index = sector.name, track.index = 2)
}, bg.border = NA)

discipline collab

Fields <- sd %>%
  mutate(
    title = str_to_lower(paper_title),
    ntitle = paste(str_to_lower(str_split_fixed(study_id, "\\_", n = 2)[,1]), paper_title, sep = " "),
    ntitle = str_squish(ntitle)
  ) %>% 
  select(ntitle, Journal_Category_Allocated_Broad)

Bib_names <- bib_sco %>% rownames_to_column(., var = "mat_names") %>% 
  mutate(TI2 = tolower(unlist(lapply(data.frame(t(str_split_fixed(TI, " ", n = 15)[,1:14])), 
                                     function(x) str_c(x, collapse  = " ")))),
         # stri_trans_general = getting rid of special letters
         name2 = stri_trans_general(tolower(str_split_fixed(SR, " ", n = 2)[,1]), "latin-ascii"),
         TI2 = paste(name2, TI2, sep= " "),
         TI2 = trimws(TI2)) %>% 
  select(TI2, mat_names)

#stringdist(Bib_names$TI2, Fields$ntitle[1], method = 'osa')
pos <- lapply(Bib_names$TI2, function(x) stringdist(Fields$ntitle, x))
pos2<- map_dbl(pos, which.min)

# these are looking good - both have the perfect matches (at least at a glance)
Bib_names$TI2
##   [1] "lamat metabolic syndrome and pesticides: a systematic review and meta-analysis"                                                              
##   [2] "yipei assessing the risk of diabetes in participants with ddt dde exposure- a systematic review"                                             
##   [3] "mota allium cepa test vs. insecticides: a scientometric and meta-analytical review"                                                          
##   [4] "he effects of perinatal exposure to endocrine-disrupting chemicals on the reproductive system of f3 generation"                              
##   [5] "liu the associations between endocrine disrupting chemicals and markers of inflammation and immune responses: a"                             
##   [6] "wang maternal exposure to pesticides and risk of autism spectrum disorders in offspring: a meta-analysis"                                    
##   [7] "sabzevari a worldwide review of currently used pesticides' monitoring in agricultural soils"                                                 
##   [8] "santana a meta-analytic review of fish antioxidant defense and biotransformation systems following pesticide exposure"                       
##   [9] "sun prenatal exposure to endocrine-disrupting chemicals and thyroid function in neonates: a systematic review and"                           
##  [10] "song association of pentachlorophenol with fetal risk of prolonged bradycardia: a systematic review and meta-analysis"                       
##  [11] "stratakis prenatal exposure to persistent organic pollutants and childhood obesity: a systematic review and meta-analysis"                   
##  [12] "hernandez-mariano exposure to the pesticide ddt and risk of diabetes and hypertension: systematic review and"                                
##  [13] "wu maternal exposure to endocrine disrupting chemicals (edcs) and preterm birth: a systematic review, meta-analysis,"                        
##  [14] "brauner endocrine disrupting chemicals and risk of testicular cancer: a systematic review and meta-analysis"                                 
##  [15] "mendes the association between environmental exposures to chlordanes, adiposity and diabetes-related features: a systematic review"          
##  [16] "vasseghian the concentration of persistent organic pollutants in water resources: a global systematic review, meta-analysis"                 
##  [17] "karalexi exposure to pesticides and childhood leukemia risk: a systematic review and meta-analysis"                                          
##  [18] "chittrakul insecticide exposure and risk of asthmatic symptoms: a systematic review and meta-analysis"                                       
##  [19] "munoz internal and maternal distribution of persistent organic pollutants in sea turtle tissues: a meta-analysis"                            
##  [20] "odutola a systematic review and meta-analysis of occupational exposures and risk of follicular lymphoma"                                     
##  [21] "santana pesticide effects on fish cholinesterase variability and mean activity: a meta-analytic review"                                      
##  [22] "amutova transfer of persistent organic pollutants in food of animal origin – meta-analysis of published"                                     
##  [23] "ma review of hexachlorocyclohexane (hch) and dichlorodiphenyltrichloroethane (ddt) contamination in chinese soils"                           
##  [24] "kachuri insecticide use and risk of non-hodgkin lymphoma subtypes: a subset meta-analysis of the north"                                      
##  [25] "tiktak are concentrations of pollutants in sharks, rays and skates (elasmobranchii) a cause for concern?"                                    
##  [26] "fu the association between environmental endocrine disruptors and cardiovascular diseases: a systematic review and meta-analysis"            
##  [27] "ribeiro exposure to endocrine-disrupting chemicals and anthropometric measures of obesity: a systematic review and meta-analysis"            
##  [28] "yang metabolomics study and meta-analysis on the association between maternal pesticide exposome and birth outcomes"                         
##  [29] "fernandes distribution of pesticides in agricultural and urban soils of brazil: a critical review"                                           
##  [30] "munoz maternal transfer of persistent organic pollutants to sea turtle eggs: a meta-analysis addressing knowledge"                           
##  [31] "sievers contaminant-induced behavioural changes in amphibians: a meta-analysis"                                                              
##  [32] "koureas spatial and temporal distribution of p,p′-dde (1‑dichloro‑2,2‑bis (p‑chlorophenyl) ethylene) blood levels across the globe."         
##  [33] "leon pesticide use and risk of non-hodgkin lymphoid malignancies in agricultural cohorts from france, norway"                                
##  [34] "wen the risk of endometriosis after exposure to endocrine-disrupting chemicals: a meta-analysis of 30 epidemiology"                          
##  [35] "spinder congenital anomalies in the offspring of occupationally exposed mothers: a systematic review and meta-analysis"                      
##  [36] "cano-sancho human epidemiological evidence about the associations between exposure to organochlorine chemicals and endometriosis: systematic"
##  [37] "van household exposure to pesticides and risk of leukemia in children and adolescents: updated systematic"                                   
##  [38] "wolfram meta-analysis of insecticides in united states surface waters: status and future implications"                                       
##  [39] "yan pesticide exposure and risk of parkinson's disease: dose-response meta-analysis of observational studies"                                
##  [40] "cano-sancho association between exposure to p,p′-ddt and its metabolite p,p′-dde with obesity: integrated systematic review"                 
##  [41] "wang identification of risk factors associated with onset and progression of amyotrophic lateral sclerosis using"                            
##  [42] "ahmed parkinson's disease and pesticides: a meta-analysis of disease connection and genetic alterations"                                     
##  [43] "van residential exposure to pesticides as risk factor for childhood and young adult brain tumors:"                                           
##  [44] "shuman-goodier a meta-analysis synthesizing the effects of pesticides on swim speed and activity of aquatic"                                 
##  [45] "yan pesticide exposure and risk of alzheimer's disease: a systematic review and meta-analysis"                                               
##  [46] "song endocrine-disrupting chemicals, risk of type 2 diabetes, and diabetes-related metabolic traits: a systematic review"                    
##  [47] "park body burden of persistent organic pollutants on hypertension: a meta-analysis"                                                          
##  [48] "meng organic contaminants in chinese sewage sludge: a meta-analysis of the literature of the past"                                           
##  [49] "luo exposure to organochlorine pesticides and non-hodgkin lymphoma: a meta-analysis of observational studies"                                
##  [50] "evangelou exposure to pesticides and diabetes: a systematic review and meta-analysis"                                                        
##  [51] "lewis-mikhael occupational exposure to pesticides and prostate cancer: a systematic review and meta-analysis"                                
##  [52] "wang the classic edcs, phthalate esters and organochlorines, in relation to abnormal sperm quality: a"                                       
##  [53] "bonde the epidemiologic evidence linking prenatal and postnatal exposure to endocrine disrupting chemicals with male"                        
##  [54] "lopez-espinosa organochlorine compounds and ultrasound measurements of fetal growth in the inma cohort (spain)"                              
##  [55] "lewis-mikhael organochlorine pesticides and prostate cancer, is there an association? a meta-analysis of epidemiological evidence"           
##  [56] "chen residential exposure to pesticide during childhood and childhood cancers: a meta-analysis"                                              
##  [57] "lim body concentrations of persistent organic pollutants and prostate cancer: a meta-analysis"                                               
##  [58] "iszatt prenatal and postnatal exposure to persistent organic pollutants and infant growth: a pooled analysis"                                
##  [59] "smit prenatal exposure to environmental chemical contaminants and asthma and eczema in school-age children"                                  
##  [60] "zheng occupational exposure to pentachlorophenol causing lymphoma and hematopoietic malignancy for two generations"                          
##  [61] "casas prenatal exposure to pcb-153, p,p'-dde and birth outcomes in 9000 mother-child pairs: exposure-response relationship"                  
##  [62] "jin pesticide exposure as a risk factor for myelodysplastic syndromes: a meta-analysis based on 1,942"                                       
##  [63] "tang exposure to organochlorine pollutants and type 2 diabetes: a systematic review and meta-analysis"                                       
##  [64] "schinasi non-hodgkin lymphoma and occupational exposure to agricultural pesticide chemical groups and active ingredients: a"                 
##  [65] "zendehdel chronic exposure to chlorophenol related compounds in the pesticide production workplace and lung cancer:"                         
##  [66] "gascon prenatal exposure to dde and pcb 153 and respiratory health in early childhood: a"                                                    
##  [67] "park exposure to dichlorodiphenyltrichloroethane and the risk of breast cancer: a systematic review and meta-analysis"                       
##  [68] "wang the difference between temperate and tropical saltwater species' acute sensitivity to chemicals is relatively"                          
##  [69] "sharma environment and human exposure to persistent organic pollutants (pops) in india: a systematic review"                                 
##  [70] "lau is an assessment factor of 10 appropriate to account for the variation in chemical"                                                      
##  [71] "ingber ddt/dde and breast cancer: a meta-analysis"                                                                                           
##  [72] "allen parkinsons disease and pesticide exposure - a new assessment"                                                                          
##  [73] "pezzoli exposure to pesticides or solvents and risk of parkinson disease"                                                                    
##  [74] "wu persistent organic pollutants and type 2 diabetes: a prospective analysis in the nurses' health"                                          
##  [75] "van parental occupational exposure to pesticides as risk factor for brain tumors in children and"                                            
##  [76] "van occupational exposure to pesticides and parkinson's disease: a systematic review and meta-analysis of cohort"                            
##  [77] "kamel pesticide exposure and amyotrophic lateral sclerosis"                                                                                  
##  [78] "henley relationships between exposure to polyhalogenated aromatic hydrocarbons and organochlorine pesticides and the risk for"               
##  [79] "van is pesticide use related to parkinson disease? some clues to heterogeneity in study results"                                             
##  [80] "govarts birth weight and prenatal exposure to polychlorinated biphenyls (pcbs) and dichlorodiphenyldichloroethylene (dde): a meta-analysis"  
##  [81] "moore paternal occupational exposure to pesticides and risk of neuroblastoma among children: a meta-analysis"                                
##  [82] "vinson exposure to pesticides and risk of childhood cancer: a meta-analysis of recent epidemiological studies"                               
##  [83] "zheng global trends and diversity in pentachlorophenol levels in the environment and in humans: a"                                           
##  [84] "chu wilms' tumour: a systematic review of risk factors and meta-analysis"                                                                    
##  [85] "riget temporal trends of legacy pops in arctic biota, an update"                                                                             
##  [86] "van childhood leukaemia and parental occupational exposure to pesticides: a systematic review and meta-analysis"                             
##  [87] "turner residential pesticides and childhood leukemia: a systematic review and meta-analysis"                                                 
##  [88] "wigle a systematic review and meta-analysis of childhood leukemia and parental occupational pesticide exposure"                              
##  [89] "perrotta multiple myeloma and farming. a systematic review of 30 years of research. where next?"                                             
##  [90] "van risk of leukaemia among pesticide manufacturing workers: a review and meta-analysis of cohort studies"                                   
##  [91] "khanjani systematic review and meta-analysis of cyclodiene insecticides and breast cancer"                                                   
##  [92] "frampton effects of pesticides on soil invertebrates in laboratory studies: a review and analysis using"                                     
##  [93] "van review and meta-analysis of risk estimates for prostate cancer in pesticide manufacturing workers"                                       
##  [94] "brown pesticides and parkinson's disease - is there a link?"                                                                                 
##  [95] "riget levels and spatial and temporal trends of contaminants in greenland biota: an updated review"                                          
##  [96] "lopez-cervantes dichlorodiphenyldichloroethane burden and breast cancer risk: a meta-analysis of the epidemiologic evidence"                 
##  [97] "ojajarvi occupational exposures and pancreatic cancer: a meta-analysis"                                                                      
##  [98] "snedaker organochlorine compounds in subtropical and tropical marine organisms: a meta-analysis"                                             
##  [99] "adami organochlorine compounds and estrogen-related cancers in women"                                                                        
## [100] "davis contamination of coastal versus open ocean surface waters. a brief meta-analysis"
Fields$ntitle[pos2]
##   [1] "s Metabolic syndrome and pesticides: A systematic review and meta-analysis."                                                                                                   
##   [2] "s Assessing the risk of diabetes in paRTIcipants with DDT DDE exposure- A systematic review and meta-analysis"                                                                 
##   [3] "s Allium cepa test vs. insecticides: a scientometric and meta-analytical review"                                                                                               
##   [4] "s Effects of�perinatal exposure to�endocrine?disrupting chemicals on�the�reproductive system of�F3 generation male rodents: a�meta?analysis"                                   
##   [5] "s The associations between endocrine disrupting chemicals and markers of inflammation and immune responses: A systematic review and meta-analysis"                             
##   [6] "s Maternal Exposure to�Pesticides and�Risk of�Autism Spectrum Disorders in�Offspring: A�Meta?analysis"                                                                         
##   [7] "s A worldwide review of currently used pesticides' monitoring in agricultural soils"                                                                                           
##   [8] "s A meta-analytic review of fish antioxidant defense and biotransformation systems following pesticide exposure"                                                               
##   [9] "s Prenatal exposure to endocrine-disrupting chemicals and thyroid function in neonates: A systematic review and meta-analysis."                                                
##  [10] "s Association of Pentachlorophenol with Fetal Risk of Prolonged Bradycardia: A Systematic Review and Meta-Analysis"                                                            
##  [11] "s Prenatal exposure to persistent organic pollutants and childhood obesity: A systematic review and meta-analysis of human studies."                                           
##  [12] "s Exposure to the pesticide DDT and risk of diabetes and hypertension: Systematic review and meta-analysis of prospective studies"                                             
##  [13] "s Maternal exposure to endocrine disrupting chemicals (EDCs) and preterm birth: A systematic review, meta-analysis, and meta-regression analysis"                              
##  [14] "s Endocrine Disrupting Chemicals and Risk of Testicular Cancer: A Systematic Review and Meta-analysis"                                                                         
##  [15] "s The association between environmental exposures to chlordanes, adiposity and diabetes-related features: a systematic review and meta-analysis."                              
##  [16] "s The concentration of persistent organic pollutants in water resources: A global systematic review, meta-analysis and probabilistic risk assessment"                          
##  [17] "s Exposure to pesticides and childhood leukemia risk: A systematic review and meta-analysis"                                                                                   
##  [18] "s Insecticide Exposure and Risk of Asthmatic Symptoms: A Systematic Review and Meta-Analysis"                                                                                  
##  [19] "s Internal and Maternal Distribution of Persistent Organic Pollutants in Sea Turtle Tissues: A Meta-Analysis."                                                                 
##  [20] "s A systematic review and meta-analysis of occupational exposures and risk of follicular lymphoma"                                                                             
##  [21] "s Pesticide effects on fish cholinesterase variability and mean activity: A meta-analytic review"                                                                              
##  [22] "s Transfer of persistent organic pollutants in food of animal origin e Meta-analysis of published data"                                                                        
##  [23] "s Review of hexachlorocyclohexane (HCH) and dichlorodiphenyltrichloroethane (DDT) contamination in Chinese soils."                                                             
##  [24] "s Insecticide use and risk of non-Hodgkin lymphoma subtypes: A subset meta-analysis of the North American Pooled Project."                                                     
##  [25] "s Are concentrations of pollutants in sharks, rays and skates (Elasmobranchii) a cause for concern? A systematic review."                                                      
##  [26] "s The association between environmental endocrine disruptors and cardiovascular diseases: A systematic review and meta-analysis"                                               
##  [27] "s Exposure to endocrine-disrupting chemicals and anthropometric measures of obesity: a systematic review and meta-analysis."                                                   
##  [28] "s Metabolomics study and meta-analysis on the association between maternal pesticide exposome and birth outcomes"                                                              
##  [29] "s Distribution of pesticides in agricultural and urban soils of Brazil: a critical review."                                                                                    
##  [30] "s Body burden of persistent organic pollutants on hypertension: a meta-analysis"                                                                                               
##  [31] "s Contaminant-induced behavioural changes in amphibians: A meta-analysis"                                                                                                      
##  [32] "s Spatial and temporal distribution of p,p'-DDE (1 dichloro 2,2 bis (p chlorophenyl) ethylene) blood levels across the globe. A systematic review and meta-analysis"           
##  [33] "s Insecticide use and risk of non-Hodgkin lymphoma subtypes: A subset meta-analysis of the North American Pooled Project."                                                     
##  [34] "s The risk of endometriosis after exposure to endocrine-disrupting chemicals: a meta-analysis of 30 epidemiology studies"                                                      
##  [35] "s Childhood leukaemia and parental occupational exposure to pesticides: a systematic review and meta-analysis"                                                                 
##  [36] "s Human epidemiological evidence about the associations between exposure to organochlorine chemicals and endometriosis: Systematic review and meta-analysis"                   
##  [37] "s Household exposure to pesticides and risk of leukemia in children and adolescents: Updated systematic review and meta-analysis"                                              
##  [38] "s Meta-Analysis of Insecticides in United States Surface Waters: Status and Future Implications."                                                                              
##  [39] "s Pesticide exposure and risk of Parkinson's disease: Dose-response metaanalysis of observational studies"                                                                     
##  [40] "s Association between Exposure to p,p0-DDT and Its Metabolite p,p0-DDE with Obesity: Integrated Systematic Review and Meta-Analysis"                                           
##  [41] "s Identification of risk factors associated with onset and progression of amyotrophic lateral sclerosis using systematic review and meta-analysis"                             
##  [42] "s Parkinson�s disease and pesticides: A meta-analysis of disease connection and genetic alterations"                                                                           
##  [43] "s Residential Exposure to Pesticide During Childhood and Childhood Cancers: A Meta-Analysis"                                                                                   
##  [44] "s A meta-analysis synthesizing the effects of pesticides on swim speed and activity of aquatic vertebrates"                                                                    
##  [45] "s Pesticide exposure and risk of Alzheimer�s disease: a systematic review and meta-analysis"                                                                                   
##  [46] "s Endocrine-disrupting chemicals, risk of type 2 diabetes, and diabetes-related metabolic traits: A systematic review and meta-analysis"                                       
##  [47] "s Body burden of persistent organic pollutants on hypertension: a meta-analysis"                                                                                               
##  [48] "s Organic Contaminants in Chinese Sewage Sludge: A meta-analysis of the Literature of the Past 30 Years."                                                                      
##  [49] "s Exposure to organochlorine pesticides and non-Hodgkin lymphoma: a meta-analysis of observational studies."                                                                   
##  [50] "s Exposure to pesticides and diabetes: A systematic review and meta-analysis"                                                                                                  
##  [51] "s Occupational exposure to pesticides and prostate cancer: a systematic review and meta-analysis"                                                                              
##  [52] "s The classic EDCs, phthalate esters and organochlorines, in relation to abnormal sperm quality: a systematic review with meta-analysis."                                      
##  [53] "s The epidemiologic evidence linking prenatal and postnatal exposure to endocrine disrupting chemicals with male reproductive disorders: a systematic review and meta-analysis"
##  [54] "s Organochlorine Compounds and Ultrasound Measurements of Fetal Growth in the INMA Cohort (Spain)."                                                                            
##  [55] "s Organochlorine pesticides and prostate cancer, Is there an association? A meta-analysis of epidemiological evidence"                                                         
##  [56] "s Residential Exposure to Pesticide During Childhood and Childhood Cancers: A Meta-Analysis"                                                                                   
##  [57] "s Body concentrations of persistent organic pollutants and prostate cancer: a meta-analysis"                                                                                   
##  [58] "s Prenatal and Postnatal Exposure to Persistent Organic Pollutants and Infant Growth: A Pooled Analysis of Seven European Birth Cohorts."                                      
##  [59] "s Prenatal exposure to environmental chemical contaminants and asthma and eczema in school-age children."                                                                      
##  [60] "s Occupational exposure to pentachlorophenol causing lymphoma and hematopoietic malignancy for two generations."                                                               
##  [61] "s Prenatal exposure to PCB-153, p,p'-DDE and birth outcomes in 9000 mother-child pairs: exposure-response relationship and effect modifiers."                                  
##  [62] "s Pesticide Exposure as a Risk Factor for Myelodysplastic Syndromes: A Meta-Analysis Based on 1,942 Cases and 5,359 Controls"                                                  
##  [63] "s Exposure to Organochlorine Pollutants and Type 2 Diabetes: A Systematic Review and Meta-Analysis"                                                                            
##  [64] "s Non-Hodgkin lymphoma and occupational exposure to agricultural pesticide chemical groups and active ingredients: a systematic review and meta-analysis."                     
##  [65] "s Chronic Exposure to Chlorophenol Related Compounds in the Pesticide Production Workplace and Lung Cancer: A MetaAnalysis"                                                    
##  [66] "s Prenatal exposure to DDE and PCB 153 and respiratory health in early childhood: a meta-analysis."                                                                            
##  [67] "s Exposure to Dichlorodiphenyltrichloroethane and the Risk of Breast Cancer: A Systematic Review and Meta-analysis."                                                           
##  [68] "s The difference between temperate and tropical saltwater species' acute sensitivity to chemicals is relatively small."                                                        
##  [69] "s Environment and human exposure to persistent organic pollutants (POPs) in India: a systematic review of recent and historical data."                                         
##  [70] "s Occupational Risk Factors for Prostate Cancer: A Meta-analysis"                                                                                                              
##  [71] "s DDT/DDE and breast cancer: A meta-analysis"                                                                                                                                  
##  [72] "s Parkinsons disease and pesticide exposure - A new assessment"                                                                                                                
##  [73] "s Exposure to pesticides or solvents and risk of Parkinson disease."                                                                                                           
##  [74] "s Persistent organic pollutants and type 2 diabetes: a prospective analysis in the nurses' health study and meta-analysis."                                                    
##  [75] "s Paternal occupational exposure to pesticides and risk of neuroblastoma among children: a meta-analysis"                                                                      
##  [76] "s Occupational exposure to pesticides and Parkinson's disease: A systematic review and meta-analysis of cohort studies"                                                        
##  [77] "s Pesticide exposure and amyotrophic lateral sclerosis"                                                                                                                        
##  [78] "s Review and meta-analysis of risk estimates for prostate cancer in pesticide manufacturing workers"                                                                           
##  [79] "s Is Pesticide Use Related to Parkinson Disease? Some Clues to Heterogeneity in Study Results"                                                                                 
##  [80] "s Birth weight and prenatal exposure to polychlorited biphenyls (PCBs) and dichlorodiphenyldichloroethylene (DDE): a meta-analysis within 12 European Birth Cohorts."          
##  [81] "s Paternal occupational exposure to pesticides and risk of neuroblastoma among children: a meta-analysis"                                                                      
##  [82] "s Exposure to pesticides and risk of childhood cancer: A meta-analysis of recent epidemiological studies"                                                                      
##  [83] "s Global Trends and Diversity in Pentachlorophenol Levels in the Environment and in Humans: A Meta-Analysis"                                                                   
##  [84] "s Wilms' tumour: A systematic review of risk factors and meta-analysis"                                                                                                        
##  [85] "s Temporal trends of legacy POPs in Arctic biota, an update."                                                                                                                  
##  [86] "s Childhood leukaemia and parental occupational exposure to pesticides: a systematic review and meta-analysis"                                                                 
##  [87] "s Residential Pesticides and Childhood Leukemia: A Systematic Review and Meta-Analysis"                                                                                        
##  [88] "s A Systematic Review and Meta-analysis of Childhood Leukemia and Parental Occupational Pesticide Exposure"                                                                    
##  [89] "s Multiple myeloma and farming. A systematic review of 30 years of research. Where next?"                                                                                      
##  [90] "s Risk of leukaemia among pesticide manufacturing workers: A review and meta-analysis of cohort studies"                                                                       
##  [91] "s Systematic Review and Meta-analysis of Cyclodiene Insecticides and Breast Cancer"                                                                                            
##  [92] "s Exposure to pesticides and diabetes: A systematic review and meta-analysis"                                                                                                  
##  [93] "s Review and meta-analysis of risk estimates for prostate cancer in pesticide manufacturing workers"                                                                           
##  [94] "s Pesticides and Parkinson�s Disease�Is There a Link?"                                                                                                                         
##  [95] "s Levels and spatial and temporal trends of contaminants in Greenland biota: an updated review."                                                                               
##  [96] "s Dichlorodiphenyldichloroethane burden and breast cancer risk: a meta-analysis of the epidemiologic evidence."                                                                
##  [97] "s Occupational exposures and pancreatic cancer: a meta-analysis."                                                                                                              
##  [98] "s Organochlorine compounds in subtropical and tropical marine organisms: a meta-analysis"                                                                                      
##  [99] "s Pesticide exposure and amyotrophic lateral sclerosis"                                                                                                                        
## [100] "s Contamination of Coastal versus Open Ocean Surface Waters"
# now we can merge two datasets 
Bib_names$Journal_Category_Allocated_Broad <- Fields$Journal_Category_Allocated_Broad[pos2]

# Creating matrix for bibliometric coupling
NetMatrix <- biblioNetwork(bib_sco, analysis = "coupling", network = "references", sep = ";")

# forcing into a nromal matrix
net_matrix <- as.matrix(NetMatrix)
diag(net_matrix) <- 0 #get rid of counts for the same papers

# replacing names with Journal_Category_Allocated_Broad
rownames(net_matrix) <- Bib_names$Journal_Category_Allocated_Broad
colnames(net_matrix) <- Bib_names$Journal_Category_Allocated_Broad





# reducing matrix according to discipline_code
rect_matrix<- t(rowsum(t(net_matrix), group = colnames(net_matrix), na.rm = T))
small_matrix <- rowsum(rect_matrix, group = rownames(rect_matrix))

# getting rid of lower triangle (as this is duplication of info)
small_matrix[lower.tri(small_matrix)] <- 0 


par(mar = c(0, 0, 0, 0), mfrow = c(1, 1))


# Create a chord diagram of the network matrix
fig5h <- chordDiagram(small_matrix, annotationTrack = "grid", preAllocateTracks = 1)
# Add a track to label each sector with its name
circos.trackPlotRegion(track.index = 1, panel.fun = function(x, y) {
  xlim = get.cell.meta.data("xlim")
  ylim = get.cell.meta.data("ylim")
  sector.name = get.cell.meta.data("sector.index")
  circos.text(mean(xlim), ylim[1] + 0.2, sector.name, facing = "clockwise", niceFacing = TRUE, adj = c(0, 0.5))
  circos.axis(h = "top", labels.cex = 0.5, major.tick.length = 0.2, sector.index = sector.name, track.index = 2)
}, bg.border = NA)

diag(small_matrix) <- 0

# Create a chord diagram of the network matrix
fig5g <- chordDiagram(small_matrix, annotationTrack = "grid", preAllocateTracks = 1)

# Add a track to label each sector with its name
circos.trackPlotRegion(track.index = 1, panel.fun = function(x, y) {
  xlim = get.cell.meta.data("xlim")
  ylim = get.cell.meta.data("ylim")
  sector.name = get.cell.meta.data("sector.index")
  circos.text(mean(xlim), ylim[1] + .1, sector.name, facing = "clockwise", niceFacing = TRUE, adj = c(0, 0.5))
  circos.axis(h = "top", labels.cex = 0.5, major.tick.length = 0.2, sector.index = sector.name, track.index = 2)
}, bg.border = NA)

CR <- citations(bib_sco, field = "article", sep = ";") #list of most cited articles
 cbind(CR$Cited[1:10]) #ten most cited articles
##                                                                                                                                                                         [,1]
## DERSIMONIAN, R., LAIRD, N., META-ANALYSIS IN CLINICAL TRIALS (1986) CONTROL CLIN TRIALS, 7, PP. 177-188                                                                    6
## HIGGINS, J.P., THOMPSON, S.G., DEEKS, J.J., ALTMAN, D.G., MEASURING INCONSISTENCY IN META-ANALYSES (2003) BMJ, 327, PP. 557-560                                            6
## BEGG, C.B., MAZUMDAR, M., OPERATING CHARACTERISTICS OF A RANK CORRELATION TEST FOR PUBLICATION BIAS (1994) BIOMETRICS, 50, PP. 1088-1101                                   5
## HIGGINS, J.P.T., THOMPSON, S.G., DEEKS, J.J., ALTMAN, D.G., MEASURING INCONSISTENCY IN META-ANALYSES (2003) BMJ, 327 (7414), PP. 557-560                                   5
## EGGER, M., DAVEY SMITH, G., SCHNEIDER, M., MINDER, C., BIAS IN META-ANALYSIS DETECTED BY A SIMPLE, GRAPHICAL TEST (1997) BMJ, 315 (7109), PP. 629-634                      4
## EGGER, M., DAVEY, S.G., SCHNEIDER, M., MINDER, C., BIAS IN META-ANALYSIS DETECTED BY A SIMPLE, GRAPHICAL TEST (1997) BMJ, 315 (7109), PP. 629-634                          4
## GREENLAND, S., QUANTITATIVE METHODS IN THE REVIEW OF EPIDEMIOLOGIC LITERATURE (1987) EPIDEMIOL REV, 9, PP. 1-30                                                            4
## HIGGINS, J.P., THOMPSON, S.G., DEEKS, J.J., ALTMAN, D.G., MEASURING INCONSISTENCY IN META-ANALYSES (2003) BMJ, 327 (7414), PP. 557-560                                     4
## PRIYADARSHI, A., KHUDER, S.A., SCHAUB, E.A., SHRIVASTAVA, S., A META-ANALYSIS OF PARKINSON'S DISEASE AND EXPOSURE TO PESTICIDES (2000) NEUROTOXICOLOGY, 21, PP. 435-440    4
## VAN MAELE-FABRY, G., WILLEMS, J.L., OCCUPATION RELATED PESTICIDE EXPOSURE AND CANCER OF THE PROSTATE: A META-ANALYSIS (2003) OCCUP ENVIRON MED, 60, PP. 634-642            4
CR <- citations(bib_sco, field = "author", sep = ";")
cbind(CR$Cited[1:10]) #ten most cited authors
##                [,1]
## BLAIR A         118
## LEE D H          69
## HOPPIN J A       61
## THOMPSON S G     52
## ZAHM S H         51
## ALTMAN D G       43
## NEEDHAM L L      41
## EGGER M          40
## GRANDJEAN P      39
## LONGNECKER M P   39
NetMatrix_coupling <- biblioNetwork(bib_sco, analysis = "coupling", network = "references", sep = "; ")
NetMatrix_coupling_plot <- networkPlot(NetMatrix_coupling, n = 20, 
                                       Title = "Paper co-citation", type = "fruchterman", size=T, 
                                       remove.multiple=FALSE, labelsize=0.8,edgesize = 5)

LS0tDQp0aXRsZTogIlNpeHR5IHllYXJzIHNpbmNlIFNpbGVudCBTcHJpbmc6IHRvd2FyZHMgYSBiYWxhbmNlZCB2aWV3IG9mIHRoZSBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGUgbGl0ZXJhdHVyZSAiDQphdXRob3I6ICJLeWxlIE1vcnJpc29uLCBDb3JhbGllIFdpbGxpYW1zLCBMb3JlbnpvIFJpY29sZmksIFllZmVuZyBZYW5nLCAgTWFsZ29yYXphdGEgTGFnaXN6LCBTaGluaWNoaSBOYWthZ2F3YSIgDQpkYXRlOiAiMjAyMy0wMy0wOSINCm91dHB1dDogDQogIHJtZGZvcm1hdHM6OmRvd25jdXRlOg0KICAgIGNvZGVfZm9sZGluZzogc2hvdw0KICAgIGNvZGVfZG93bmxvYWQ6IHRydWUNCiAgICB0b2NfZGVwdGg6IDQNCmVkaXRvcl9vcHRpb25zOiANCiAgY2h1bmtfb3V0cHV0X3R5cGU6IGNvbnNvbGUNCi0tLQ0KYGBge3IsIGluY2x1ZGUgPSBGQUxTRX0NCnJtKGxpc3QgPSBscygpKQ0KIyBrbml0ciBzZXR0aW5nDQprbml0cjo6b3B0c19jaHVuayRzZXQoDQogIG1lc3NhZ2UgPSBGQUxTRSwNCiAgd2FybmluZyA9IEZBTFNFLCANCiAgY2FjaGUgPSBUUlVFLA0KICBlY2hvPVRSVUUNCikNCmBgYA0KDQoNCg0KDQpJbiB0aGlzIFJtYXJrZG93biBkb2N1bWVudCB3ZSBwcm92aWRlIHRoZSBmb2xsb3dpbmcgd29ya2Zsb3c6ICAgDQoNCg0KLSBPYmplY3RpdmUgMCAtIFRvIGV4YW1pbmUgdGhlIHZvbHVtZSBhbmQgdGVtcG9yYWwgdHJlbmRzIG9mIGV4aXN0aW5nIG1ldGEtYW5hbHlzZXMgb24gdGhlIGVmZmVjdHMgb2Ygb3JnYW5vY2hsb3JpbmUgcGVzdGljaWRlcw0KLSBPYmplY3RpdmUgMTogVG8gZXZhbHVhdGUgdGhlIG1ldGhvZG9sb2dpY2FsIHBhdHRlcm5zIGFuZCBxdWFsaXR5IG9mIGV4aXN0aW5nIG1ldGEtYW5hbHlzZXMgc3R1ZHlpbmcgdGhlIGVmZmVjdHMgb2Ygb3JnYW5vY2hsb3JpbmUgcGVzdGljaWRlcy4NCi0gT2JqZWN0aXZlIDIgLiBUbyBleHBsb3JlIHRoZSB2YXJpb3VzIGNoYXJhY3RlcmlzdGljcyBvZiB0aGUgb3JnYW5vY2hsb3JpbmUgcGVzdGljaWRlcyBsaXRlcmF0dXJlIHN1Y2ggYXMgdGhlIHBlc3RpY2lkZXMgdXNlZCwgdGhlIGltcGFjdHMgZWxpY2l0ZWQgaW4gcmVzcG9uc2UgYW5kIHRoZSBzdWJqZWN0cyB0aGF0IHdlcmUgaW52ZXN0aWdhdGVkLiANCg0KDQogDQogLSBPYmplY3RpdmUgNCAtIFRvIGludmVzdGlnYXRlIHRoZSByZXNlYXJjaCBvdXRwdXRzIGFjcm9zcyBkaWZmZXJlbnQgY291bnRyaWVzIGFuZCBjb250aW5lbnRzIGFuZCBpbnZlc3RpZ2F0ZSB0aGUgZGVncmVlIG9mIGNyb3NzLWNvdW50cnkgY29sbGFib3JhdGlvbi4NCiANCg0KIyAqKkxvYWQgcGFja2FnZXMgYW5kIGRhdGEqKg0KDQojIyBMb2FkIFBhY2thZ2VzIA0KDQpgYGB7ciwgcmVzdWx0cz0iaGlkZSJ9DQpybShsaXN0ID0gbHMoKSkNCnBhY21hbjo6cF9sb2FkKHRpZHl2ZXJzZSwNCmhyYnJ0aGVtZXMsIA0KcGF0Y2h3b3JrLA0KaGVyZSwNCnN0cmluZ3IsDQprbml0ciwNCmZvcm1hdFIsDQpmb3JjYXRzLA0KZ2dwbG90MiwNCmJpYmxpb21ldHJpeCwNCmlncmFwaCwNCnN0cmluZ2ksDQpzdHJpbmdkaXN0LA0KY2lyY2xpemUsDQpnZ2FsbHV2aWFsLA0KZ2dyYXBoKQ0Ka25pdHI6Om9wdHNfY2h1bmskc2V0KGVjaG8gPSBUUlVFLCBtZXNzYWdlID0gRkFMU0UsIHdhcm5pbmcgPSBGQUxTRSkNCg0KYGBgDQoNCg0KIyMgTG9hZCBkYXRhDQoNCk1hbnVhbGx5IGV4dHJhY3RlZCBwaWxvdCBkYXRhIGlzIHN0b3JlZCBpbiBmaXZlIHNlcGFyYXRlICoqLmNzdioqIGZpbGVzIHJlcHJlc2VudGluZyBkaWZmZXJlbnQgYXNwZWN0cyBvZiB0aGUgZGF0YSAoZXh0cmFjdGVkIHZpYSBzdHJ1Y3R1cmVkIHByZWRlZmluZWQgR29vZ2xlIEZvcm1zIC0gb25lIHBlciB0YWJsZSkuIA0KDQpCaWJsaW9ncmFwaGljIGRhdGEgcmVjb3JkcyBhcmUgZXhwb3J0ZWQgZnJvbSBTY29wdXMgKGluY2x1ZGluZyBjaXRlZCByZWZlcmVuY2VzIGZpZWxkKSBpbiAuYmliIGZvcm1hdCBhbmQgbG9jYWxseSBzYXZlZCBhcyAqKnNjb3B1cy5iaWIqKi4gDQpgYGB7cn0NCiMgTG9hZCBDU1YgZGF0YXNldHMNCnNkIDwtIHJlYWRfY3N2KGhlcmUoImRhdGEiLCAib2NwX3NybV9zdHVkeV9kZXRhaWxzLmNzdiIpKQ0Kb2NwIDwtIHJlYWRfY3N2KGhlcmUoImRhdGEiLCAib2NwX3NybV9vY3BfZGV0YWlscy5jc3YiKSkNCnN1YiA8LSByZWFkX2NzdihoZXJlKCJkYXRhIiwgIm9jcF9zcm1fc3ViamVjdF9kZXRhaWxzLmNzdiIpKQ0KaW0gPC0gcmVhZF9jc3YoaGVyZSgiZGF0YSIsICJvY3Bfc3JtX2ltcGFjdF9kZXRhaWxzLmNzdiIpKQ0Kc3AgPC0gcmVhZF9jc3YoaGVyZSgiZGF0YSIsICJvY3Bfc3JtX3NwZWNpZXNfZGV0YWlscy5jc3YiKSkNCg0KIyBMb2FkIEJpYlRlWCBkYXRhc2V0DQpiaWJfc2NvIDwtIGNvbnZlcnQyZGYoaGVyZSgiZGF0YSIsICJiaWJfc2NvLmJpYiIpLCBkYnNvdXJjZSA9ICJzY29wdXMiLCBmb3JtYXQgPSAiYmlidGV4IikNCmBgYA0KDQojIE9iamVjdGl2ZSAwIC0gVG8gZXhhbWluZSB0aGUgdm9sdW1lIGFuZCB0ZW1wb3JhbCB0cmVuZHMgb2YgZXhpc3RpbmcgbWV0YS1hbmFseXNlcyBvbiB0aGUgZWZmZWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzDQoNCiMjIEZpZ3VyZSAxIA0KYSkgQSBiYXIgcGxvdCBzaG93aW5nIHRoZSB0aW1lIHRyZW5kcyBvZiBtZXRhLWFuYWx5c2lzIGludmVzdGlnYXRpbmcgdGhlIGltcGFjdHMgb2Ygb3JnYW5vY2hsb3JpbmUgcGVzdGljaWRlcy4gVGhlIGNvbG91cnMgcmVwcmVzZW50IHRoZSBzdWJqZWN0cyBpbiB3aGljaCB0aGUgaW1wYWN0cyB3ZXJlIGludmVzdGlnYXRlZC4gDQpiKSBBbiBhcmVhIHBsb3Qgc2hvd2luZyB0aGUgY3VtbXVsYXRpdmUgdGltZSB0cmVuZCBvZiBtZXRhLWFuYWx5c2lzIGludmVzdGlnYXRpbmcgdGhlIGltcGFjdHMgb2Ygb3JnYW5vY2hsb3JpbmUgcGVzdGljaWRlcy4gVGhlIGNvbG91cnMgcmVwcmVzZW50IHRoZSBzdWJqZWN0cyBpbiB3aGljaCB0aGUgaW1wYWN0cyB3ZXJlIGludmVzdGlnYXRlZC4gDQpgYGB7ciwgZmlnLndpZHRoPTE2LCBmaWcuaGVpZ2h0PTEyfQ0KDQojIEpvaW4gdGhlIHN0dWR5IGFuZCBzdWJqZWN0IGRhdGFzZXRzDQpzZF9zdWIgPC0gbGVmdF9qb2luKHNkLCBzdWIsIGJ5ID0gInN0dWR5X2lkIikNCg0KIyBDb3VudCB0aGUgbnVtYmVyIG9mIHB1YmxpY2F0aW9ucyBwZXIgeWVhciBhbmQgY2FsY3VsYXRlIGN1bXVsYXRpdmUgc3VtDQpzZDEgPC0gc2QgJT4lDQogIGNvdW50KHB1YmxpY2F0aW9uX3llYXIpICU+JQ0KICBtdXRhdGUobl9jdW11bGF0aXZlID0gY3Vtc3VtKG4pKQ0KDQojIENyZWF0ZSB0aGUgYW5udWFsIGNvdW50IHBsb3QNCmZpZzFhIDwtIHNkX3N1YiAlPiUNCiAgbXV0YXRlKHN1YmplY3RzID0gc3Ryc3BsaXQoc3ViamVjdCwgIixcXHMrIikpICU+JQ0KICB1bm5lc3Qoc3ViamVjdHMpICU+JQ0KICBjb3VudChwdWJsaWNhdGlvbl95ZWFyLCBzdWJqZWN0cykgJT4lDQogIGdyb3VwX2J5KHN1YmplY3RzID0gcmVvcmRlcihzdWJqZWN0cywgbikpICU+JQ0KICBnZ3Bsb3QoYWVzKHggPSBwdWJsaWNhdGlvbl95ZWFyLCB5ID0gbiwgZmlsbCA9IHN1YmplY3RzKSkgKw0KICAgIGdlb21fYmFyKHN0YXQgPSAiaWRlbnRpdHkiLCBwb3NpdGlvbiA9ICJzdGFjayIsIGFscGhhID0gMC43KSArDQogICAgZ2VvbV90ZXh0KGFlcyhsYWJlbCA9IG4pLCBwb3NpdGlvbiA9IHBvc2l0aW9uX3N0YWNrKHZqdXN0ID0gMC42KSwgDQogICAgICAgICAgICAgIGZvbnRmYWNlID0gImJvbGQiLCBjb2xvciA9ICJ3aGl0ZSIsIHNpemUgPSA2LCBoanVzdCA9IDAuNCkgKw0KICAgIHNjYWxlX3hfY29udGludW91cyhicmVha3MgPSBzZXEobWluKHNkMSRwdWJsaWNhdGlvbl95ZWFyKSwgbWF4KHNkMSRwdWJsaWNhdGlvbl95ZWFyKSwgYnkgPSAxKSwgDQogICAgICAgICAgICAgICAgICAgICAgIGV4cGFuZCA9IGV4cGFuc2lvbigwLDApKSArICANCiAgICBzY2FsZV95X2NvbnRpbnVvdXMoIkFubnVhbCBBcnRpY2xlIENvdW50IiwgbGltaXRzID0gYygwLDE1KSkgKw0KICAgIHRoZW1lX21pbmltYWwoKSArDQogICAgbGFicyh5ID0gIkFydGljbGUgQ291bnQiLCB0YWcgPSAiQSIsIGZpbGwgPSAiU3ViamVjdHMiKSArDQogICAgdGhlbWUoDQogICAgICBwYW5lbC5ncmlkLm1ham9yLnkgPSBlbGVtZW50X2xpbmUoY29sb3IgPSAiZ3JheSIsIGxpbmV0eXBlID0gImRhc2hlZCIpLA0KICAgICAgcGFuZWwuZ3JpZC5taW5vci55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgYXhpcy5saW5lLnggPSBlbGVtZW50X2xpbmUoc2l6ZSA9IDEuMiksDQogICAgICBheGlzLmxpbmUueSA9IGVsZW1lbnRfbGluZShzaXplID0gMS4yKSwNCiAgICAgIGF4aXMudGl0bGUueCA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgIGF4aXMudGl0bGUueSA9IGVsZW1lbnRfdGV4dChzaXplID0gMjAsIGZhY2UgPSAiYm9sZCIpLA0KICAgICAgYXhpcy50ZXh0LnggPSBlbGVtZW50X3RleHQoYW5nbGUgPSA0NSwgaGp1c3QgPSAxLCBzaXplID0gMTUsIGNvbG9yID0gIiM2NjY2NjYiKSwNCiAgICAgIGF4aXMudGV4dC55ID0gZWxlbWVudF90ZXh0KHNpemUgPSAyMCwgY29sb3IgPSAiIzY2NjY2NiIpLA0KICAgICAgbGVnZW5kLnRleHQgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDE1KSwNCiAgICAgIGxlZ2VuZC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplID0gMTUpLA0KICAgICAgbGVnZW5kLnBvc2l0aW9uID0gYygwLCAxKSwNCiAgICAgIGxlZ2VuZC5qdXN0aWZpY2F0aW9uID0gYygwLCAxKQ0KICAgICkgKw0KICAgIHNjYWxlX2ZpbGxfYnJld2VyKHBhbGV0dGUgPSAiRGFyazIiKSArDQogICAgZ3VpZGVzKGZpbGwgPSBndWlkZV9sZWdlbmQob3ZlcnJpZGUuYWVzID0gbGlzdChzaXplPTEwKSkpDQoNCiMgQ3JlYXRlIHRoZSBjdW11bGF0aXZlIGNvdW50IHBsb3QNCmZpZzFiIDwtIHNkX3N1YiAlPiUNCiAgbXV0YXRlKHN1YmplY3RzID0gc3Ryc3BsaXQoc3ViamVjdCwgIixcXHMrIikpICU+JQ0KICB1bm5lc3Qoc3ViamVjdHMpICU+JQ0KICBjb3VudChwdWJsaWNhdGlvbl95ZWFyLCBzdWJqZWN0cykgJT4lDQogIGdyb3VwX2J5KHN1YmplY3RzID0gcmVvcmRlcihzdWJqZWN0cywgbikpICU+JQ0KICBtdXRhdGUobl9jdW11bGF0aXZlID0gY3Vtc3VtKG4pKSAlPiUNCiAgZ2dwbG90KGFlcyh4ID0gcHVibGljYXRpb25feWVhciwgeSA9IG5fY3VtdWxhdGl2ZSwgZmlsbCA9IHN1YmplY3RzKSkgKw0KICAgIGdlb21fYXJlYShzaXplID0gMS4yLCBhbHBoYSA9IDAuNykgKw0KICAgIHNjYWxlX3lfY29udGludW91cygiQ3VtdWxhdGl2ZSBBcnRpY2xlIENvdW50IiwgbGltaXRzID0gYygwLDExNSkpICsNCiAgICBzY2FsZV94X2NvbnRpbnVvdXMoYnJlYWtzID0gc2VxKG1pbihzZF9zdWIkcHVibGljYXRpb25feWVhciksIG1heChzZF9zdWIkcHVibGljYXRpb25feWVhciksIGJ5ID0gMSksIA0KICAgICAgICAgICAgICAgICAgICAgICBleHBhbmQgPSBleHBhbnNpb24oMCwwKSkgKyAgDQogICAgdGhlbWVfbWluaW1hbCgpICsNCiAgICBsYWJzKHggPSAiWWVhciIsIHkgPSAiQ3VtdWxhdGl2ZSBBcnRpY2xlIENvdW50IiwgdGFnID0gIkIiLCBmaWxsID0gIlN1YmplY3RzIikgKw0KICAgIHRoZW1lKA0KICAgICAgcGFuZWwuZ3JpZC5tYWpvci55ID0gZWxlbWVudF9saW5lKGNvbG9yID0gImdyYXkiLCBsaW5ldHlwZSA9ICJkYXNoZWQiKSwNCiAgICAgIHBhbmVsLmdyaWQubWlub3IueSA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgIGF4aXMubGluZS54ID0gZWxlbWVudF9saW5lKHNpemUgPSAxLjIpLA0KICAgICAgYXhpcy5saW5lLnkgPSBlbGVtZW50X2xpbmUoc2l6ZSA9IDEuMiksDQogICAgICBheGlzLnRpdGxlLnggPSBlbGVtZW50X3RleHQoc2l6ZSA9IDIwLCBmYWNlID0gImJvbGQiKSwNCiAgICAgIGF4aXMudGl0bGUueSA9IGVsZW1lbnRfdGV4dChzaXplID0gMjAsIGZhY2UgPSAiYm9sZCIpLA0KICAgICAgYXhpcy50ZXh0LnggPSBlbGVtZW50X3RleHQoYW5nbGUgPSA0NSwgaGp1c3QgPSAxLCBzaXplID0gMTUsIGNvbG9yID0gIiM2NjY2NjYiKSwNCiAgICAgIGF4aXMudGV4dC55ID0gZWxlbWVudF90ZXh0KHNpemUgPSAyMCwgY29sb3IgPSAiIzY2NjY2NiIpLA0KICAgICAgbGVnZW5kLnBvc2l0aW9uID0gIm5vbmUiDQogICAgKSArDQogICAgc2NhbGVfZmlsbF9icmV3ZXIocGFsZXR0ZSA9ICJEYXJrMiIpICsNCiAgICBndWlkZXMoZmlsbCA9IGd1aWRlX2xlZ2VuZChvdmVycmlkZS5hZXMgPSBsaXN0KHNpemU9MTApKSkNCg0KIyBDb21iaW5lIHRoZSB0d28gcGxvdHMNCmZpZzEgPC0gZmlnMWEgLyBmaWcxYg0KZmlnMQ0KDQogIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZzEucGRmIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEyLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KICBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWcxLmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMiwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCmBgYA0KDQojIyBGaWd1cmUgczQgDQphKSBBIGJhciBwbG90IHNob3dpbmcgdGhlIHRpbWUgdHJlbmRzIG9mIG1ldGEtYW5hbHlzaXMgaW52ZXN0aWdhdGluZyB0aGUgaW1wYWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiANCmIpIEFuIGFyZWEgcGxvdCBzaG93aW5nIHRoZSBjdW1tdWxhdGl2ZSB0aW1lIHRyZW5kIG9mIG1ldGEtYW5hbHlzaXMgaW52ZXN0aWdhdGluZyB0aGUgaW1wYWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiANCmBgYHtyLCBmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTJ9DQojIENyZWF0ZSB0aGUgYW5udWFsIENvdW50IFBsb3QNCmZpZ3M0YSA8LSBzZDEgJT4lDQogIGdncGxvdChhZXMoeCA9IHB1YmxpY2F0aW9uX3llYXIsIHkgPSBuKSkgKw0KICAgIGdlb21fY29sKGZpbGwgPSAiIzFiOWU3NyIsIGFscGhhID0gMC43KSArDQogICAgZ2VvbV90ZXh0KGFlcyhsYWJlbCA9IG4pLCBwb3NpdGlvbiA9IHBvc2l0aW9uX3N0YWNrKHZqdXN0ID0gMC42KSwgDQogICAgICAgICAgICAgIGZvbnRmYWNlID0gImJvbGQiLCBjb2xvciA9ICJ3aGl0ZSIsIHNpemUgPSA2LCBoanVzdCA9IDAuNCkgKw0KICAgIHNjYWxlX3hfY29udGludW91cyhicmVha3MgPSBzZXEobWluKHNkMSRwdWJsaWNhdGlvbl95ZWFyKSwgbWF4KHNkMSRwdWJsaWNhdGlvbl95ZWFyKSwgYnkgPSAxKSwgDQogICAgICAgICAgICAgICAgICAgICAgIGV4cGFuZCA9IGV4cGFuc2lvbigwLDEpKSArDQogICAgc2NhbGVfeV9jb250aW51b3VzKCJBbm51YWwgQXJ0aWNsZSBDb3VudCIsIGxpbWl0cyA9IGMoMCwxNSkpICsNCiAgICBsYWJzKHggPSAiWWVhciIsIHRhZyA9ICJBIikgKw0KICAgIHRoZW1lX21pbmltYWwoKSArDQogICAgdGhlbWUoDQogICAgICBwYW5lbC5ncmlkLm1ham9yLnkgPSBlbGVtZW50X2xpbmUoY29sb3IgPSAiZ3JheSIsIGxpbmV0eXBlID0gImRhc2hlZCIpLA0KICAgICAgcGFuZWwuZ3JpZC5taW5vci55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgYXhpcy5saW5lLnggPSBlbGVtZW50X2xpbmUoc2l6ZSA9IDEuMiksDQogICAgICBheGlzLmxpbmUueSA9IGVsZW1lbnRfbGluZShzaXplID0gMS4yKSwNCiAgICAgIGF4aXMudGl0bGUueCA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgIGF4aXMudGl0bGUueSA9IGVsZW1lbnRfdGV4dChzaXplID0gMjAsIGZhY2UgPSAiYm9sZCIpLA0KICAgICAgYXhpcy50ZXh0LnggPSBlbGVtZW50X3RleHQoYW5nbGUgPSA0NSwgaGp1c3QgPSAxLCBzaXplID0gMTUsIGNvbG9yID0gIiM2NjY2NjYiKSwNCiAgICAgIGF4aXMudGV4dC55ID0gZWxlbWVudF90ZXh0KHNpemUgPSAyMCwgY29sb3IgPSAiIzY2NjY2NiIpLA0KICAgICAgbGVnZW5kLnBvc2l0aW9uID0gIm5vbmUiDQogICAgKQ0KDQojIENyZWF0ZSB0aGUgY3VtdWxhdGl2ZSBDb3VudCBQbG90DQpmaWdzNGIgPC0gc2QxICU+JQ0KICBnZ3Bsb3QoYWVzKHggPSBwdWJsaWNhdGlvbl95ZWFyLCB5ID0gbl9jdW11bGF0aXZlKSkgKw0KICAgIGdlb21fbGluZShjb2xvciA9ICIjNzU3MGIzIiwgc2l6ZSA9IDEsIGxpbmV0eXBlID0gInNvbGlkIikgKw0KICAgIGdlb21fcG9pbnQoc2hhcGUgPSAyMSwgc2l6ZSA9IDYsIGZpbGwgPSAiIzc1NzBiMyIsIHN0cm9rZSA9IDApICsNCiAgICBnZW9tX3RleHQoYWVzKGxhYmVsID0gbl9jdW11bGF0aXZlKSwgaGp1c3QgPSAwLjIsIHZqdXN0ID0gLTEsIHNpemUgPSA2LCBjb2xvciA9ICJibGFjayIpICsNCiAgICBzY2FsZV94X2NvbnRpbnVvdXMoYnJlYWtzID0gc2VxKG1pbihzZDEkcHVibGljYXRpb25feWVhciksIG1heChzZDEkcHVibGljYXRpb25feWVhciksIGJ5ID0gMSksIA0KICAgICAgICAgICAgICAgICAgICAgICBleHBhbmQgPSBleHBhbnNpb24oMCwxKSkgKw0KICAgIHNjYWxlX3lfY29udGludW91cygiQ3VtdWxhdGl2ZSBBcnRpY2xlIENvdW50IiwgbGltaXRzID0gYygwLDEyMCkpICsNCiAgICBsYWJzKHggPSAiWWVhciIsIHRhZyA9ICJCIikgKw0KICAgIHRoZW1lX21pbmltYWwoKSArDQogICAgdGhlbWUoDQogICAgICBwYW5lbC5ncmlkLm1ham9yLnkgPSBlbGVtZW50X2xpbmUoY29sb3IgPSAiZ3JheSIsIGxpbmV0eXBlID0gImRhc2hlZCIpLA0KICAgICAgcGFuZWwuZ3JpZC5taW5vci55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgYXhpcy5saW5lLnggPSBlbGVtZW50X2xpbmUoc2l6ZSA9IDEuMiksDQogICAgICBheGlzLmxpbmUueSA9IGVsZW1lbnRfbGluZShzaXplID0gMS4yKSwNCiAgICAgIGF4aXMudGl0bGUueCA9IGVsZW1lbnRfdGV4dChzaXplID0gMjAsIGZhY2UgPSAiYm9sZCIpLA0KICAgICAgYXhpcy50aXRsZS55ID0gZWxlbWVudF90ZXh0KHNpemUgPSAyMCwgZmFjZSA9ICJib2xkIiksDQogICAgICBheGlzLnRleHQueCA9IGVsZW1lbnRfdGV4dChhbmdsZSA9IDQ1LCBoanVzdCA9IDEsIHNpemUgPSAxNSwgY29sb3IgPSAiIzY2NjY2NiIpLA0KICAgICAgYXhpcy50ZXh0LnkgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDIwLCBjb2xvciA9ICIjNjY2NjY2IiksDQogICAgICBsZWdlbmQucG9zaXRpb24gPSAibm9uZSINCiAgICApDQoNCiMgQ29tYmluZSB0aGUgdHdvIHBsb3RzDQpmaWdzNCA8LSBmaWdzNGEgLyBmaWdzNGINCmZpZ3M0DQoNCiAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczQucGRmIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEyLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KICBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzNC5qcGciKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTIsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQoNCmBgYA0KDQojIE9iamVjdGl2ZSAxOiBUbyBldmFsdWF0ZSB0aGUgbWV0aG9kb2xvZ2ljYWwgcGF0dGVybnMgYW5kIHF1YWxpdHkgb2YgZXhpc3RpbmcgbWV0YS1hbmFseXNlcyBzdHVkeWluZyB0aGUgZWZmZWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiANCg0KIyMgRmlndXJlIHM1IA0KQSBiYXIgcGxvdCBzaG93aW5nIHRoZSBwZXJjZW50YWdlIGFuZCB0b3RhbCBjb3VudCBvZiBzY2llbnRpZmljIGxpdGVyYXR1cmUgZGF0YWJhc2VzIHVzZWQgaW4gbWV0YS1hbmFseXNpcyBpbnZlc3RpZ2F0aW5nIHRoZSBpbXBhY3RzIG9mIG9yZ2Fub2NobG9yaW5lIHBlc3RpY2lkZXMuIE5vdGU6IHNvbWUgbWV0YS1hbmFseXNpcyBtYXkgY29udHJpYnV0ZSB0byBtdWx0aXBsZSBzZWN0aW9ucyBpZiB0aGUgc3R1ZHkgaW52b2x2ZXMgbXVsdGlwbGUgc2NpZW50aWZpYyBsaXRlcmF0dXJlIGRhdGFiYXNlcy4g4oCcT3RoZXIgZGF0YWJhc2Vz4oCdIGlzIGFsbCBvdGhlciBkYXRhYmFzZXMgd2l0aCBhIGNvdW50IGxlc3MgdGhhbiBvciBlcXVhbCB0byAzDQpgYGB7ciwgZmlnLndpZHRoPTE2LCBmaWcuaGVpZ2h0PTEwfQ0KIyBDYWxjdWxhdGUgdGhlIHRvdGFsIGNvdW50IGZvciBlYWNoIGNhdGVnb3J5DQpkYXRhYmFzZV9jb3VudCA8LSBzZCAlPiUgDQogIHNlcGFyYXRlX3Jvd3MoZGF0YWJhc2Vfc2VhcmNoLCBzZXAgPSAiLFxccysiKSAlPiUgDQogIGNvdW50KGRhdGFiYXNlX3NlYXJjaCkgJT4lIA0KICBmaWx0ZXIoZGF0YWJhc2Vfc2VhcmNoICE9ICJub3QgcmVwb3J0ZWQiKSAlPiUgDQogIGFycmFuZ2UoZGVzYyhuKSkgJT4lIA0KICBtdXRhdGUoZGF0YWJhc2Vfc2VhcmNoID0gaWZlbHNlKG48PSAzLCAiT3RoZXIgZGF0YWJhc2VzIiwgYXMuY2hhcmFjdGVyKGRhdGFiYXNlX3NlYXJjaCkpKSAlPiUgDQogICAgZ3JvdXBfYnkoZGF0YWJhc2Vfc2VhcmNoKSAlPiUNCiAgc3VtbWFyaXNlKG4gPSBzdW0obikpDQoNCg0KIyBDYWxjdWxhdGUgcHJvcG9ydGlvbiBhbmQgcGVyY2VudGFnZSBmb3IgZWFjaCBjYXRlZ29yeQ0KZGF0YWJhc2VfcGN0IDwtIGRhdGFiYXNlX2NvdW50ICU+JQ0KICBtdXRhdGUocHJvcG9ydGlvbiA9IG4gLyBzdW0oZGF0YWJhc2VfY291bnQkbiksDQogICAgICAgICBwZXJjZW50YWdlID0gcHJvcG9ydGlvbiAqIDEwMCkNCg0KIyBDcmVhdGUgYSBzdGFuZGFyZCB0aGVtZSBmb3IgdGhlIHN1cHBsZW1lbnQgcGxvdHMNCnRoZW1lX3N1cHBsIDwtIGZ1bmN0aW9uKCkgew0KICB0aGVtZV9taW5pbWFsKCkgKw0KICB0aGVtZSgNCiAgICBheGlzLnRleHQueSA9IGVsZW1lbnRfdGV4dChzaXplID0gMTUpLA0KICAgIGF4aXMudGV4dC54ID0gZWxlbWVudF90ZXh0KHNpemUgPSAxNSksDQogICAgYXhpcy5saW5lLnggPSBlbGVtZW50X2xpbmUoY29sb3IgPSAiZ3JheSIsIHNpemUgPSAwLjUpLA0KICAgIGF4aXMubGluZS55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgIGF4aXMudGlja3MueCA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICBheGlzLnRpY2tzLnkgPSBlbGVtZW50X2JsYW5rKCksDQogICAgYXhpcy50aXRsZS54ID0gZWxlbWVudF90ZXh0KHNpemUgPSAyMCksDQogICAgYXhpcy50aXRsZS55ID0gZWxlbWVudF90ZXh0KHNpemUgPSAyMCksDQogICAgcGFuZWwuZ3JpZC5tYWpvci55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgIHBhbmVsLmdyaWQubWlub3IueSA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICBsZWdlbmQucG9zaXRpb24gPSAibm9uZSINCiAgKQ0KfQ0KDQojIENyZWF0ZSB0aGUgY291bnQgcGxvdA0KZmlnczUgPC0gZGF0YWJhc2VfY291bnQgJT4lDQogIGdncGxvdChhZXMoeCA9IG4sIHkgPSByZW9yZGVyKGRhdGFiYXNlX3NlYXJjaCwgbiksIGZpbGwgPSAiIzFiOWU3NyIpKSArDQogIGdlb21fYmFyKHN0YXQgPSAiaWRlbnRpdHkiLCB3aWR0aCA9IDAuOCAsIGFscGhhID0gMC43KSArDQogIGdlb21fdGV4dChhZXMobGFiZWwgPSBuLCB4ID0gbiAvIDIsIHkgPSByZW9yZGVyKGRhdGFiYXNlX3NlYXJjaCwgbikpLCBoanVzdCA9IDAuNSwgc2l6ZSA9IDYsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoZGF0YSA9IGRhdGFiYXNlX3BjdCwgYWVzKGxhYmVsID0gcGFzdGUwKCIoIiwgcm91bmQocGVyY2VudGFnZSwgMSksICIlKSIpLCB4ID0gbiksIA0KICAgICAgICAgICAgaGp1c3QgPSAtMC4xLCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siLCBmb250ZmFjZSA9ICJib2xkIikgKw0KICBzY2FsZV9maWxsX2lkZW50aXR5KGd1aWRlID0gIm5vbmUiKSArDQogIHNjYWxlX3lfZGlzY3JldGUobmFtZSA9ICJEYXRhYmFzZSBTZWFyY2giKSArDQogIHNjYWxlX3hfY29udGludW91cyhuYW1lID0gIkFydGljbGUgQ291bnQiLCBleHBhbmQgPSBjKDAsIDApLCBsaW1pdHMgPSBjKDAsIG1heChkYXRhYmFzZV9jb3VudCRuKSoxLjEpKSArDQogIGxhYnMoeSA9IE5VTEwpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzNQ0KDQogIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3M1LnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczUuanBnIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KDQpgYGANCg0KIyMgRmlndXJlIHM2DQpBbiBhbGx1dmlhbCBwbG90IHNob3dpbmcgdGhlIHJlbGF0aW9uc2hpcCBiZXR3ZWVuIHRoZSBKb3VybmFsIENpdGF0aW9uIFJlcG9ydCBDYXRlZ29yeSBhbmQgdGhlIHNjaWVudGlmaWMgbGl0ZXJhdHVyZSBkYXRhYmFzZSB1c2VkLiBGaWx0ZXJlZCBmb3Igc2NpZW50aWZpYyBsaXRlcmF0dXJlIGRhdGFiYXNlIGNvdW50cyBncmVhdGVyIHRoYW4gb3IgZXF1YWwgdG8gMw0KYGBge3IsIGZpZy53aWR0aD0xNiwgZmlnLmhlaWdodD0xMH0NCiMgUmVuYW1lIEVudmlyb25tZW50YWwgU2NpZW5jZQ0Kc2QgPC0gc2QgJT4lDQogIG11dGF0ZShKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCA9IHN0cl9yZXBsYWNlKEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCAiRW52aXJvbm1lbnRhbCBTY2llbmNlIiwgIkVudmlyb25tZW50YWxcblNjaWVuY2UiKSkNCg0KIyBEYXRhIFRyYW5zZm9ybWF0aW9uIA0KZGF0YWJhc2VfYWxsdXZpYWwgPC0gc2QgJT4lIA0KICAgIHNlcGFyYXRlX3Jvd3MoZGF0YWJhc2Vfc2VhcmNoLCBzZXAgPSAiLFxccysiKSAlPiUNCiAgICBncm91cF9ieShKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgZGF0YWJhc2Vfc2VhcmNoKSAlPiUgDQogICAgY291bnQoZGF0YWJhc2Vfc2VhcmNoLCBKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCkgJT4lIA0KICAgIHN1bW1hcmlzZShmcmVxID0gbigpLCAuZ3JvdXBzID0gJ2Ryb3AnKSAlPiUgDQogICAgZ3JvdXBfYnkoZGF0YWJhc2Vfc2VhcmNoKSAlPiUgDQogICAgZmlsdGVyKHN1bShmcmVxKSA+PSAzKSAlPiUgDQogICAgZmlsdGVyKGRhdGFiYXNlX3NlYXJjaCAhPSAiTkEiKQ0KDQojIENyZWF0ZSB0aGUgQWxsdXZpYWwgcGxvdA0KZmlnczYgPC0gZGF0YWJhc2VfYWxsdXZpYWwgJT4lIA0KZ2dwbG90KGFlcyh5ID0gZnJlcSAsYXhpczEgPSBKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgYXhpczIgPSBkYXRhYmFzZV9zZWFyY2gpKSArDQogIHNjYWxlX3hfZGlzY3JldGUobGltaXRzID0gYygiSm91cm5hbCBDaXRhdGlvbiBSZXBvcnQgQ2F0ZWdvcnkiLCAiRGF0YWJhc2UgU2VhcmNoIiksIGV4cGFuZCA9IGMoLjA1LCAuMDUpKSArDQogIHhsYWIoIlZhcmlhYmxlcyIpICsNCiAgeWxhYigiRnJlcXVlbmN5IikgKw0KICBnZW9tX2FsbHV2aXVtKGFlcyhmaWxsID0gSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpKSArDQogIGdlb21fc3RyYXR1bSh3aWR0aCA9IDEvNC41LCBmaWxsID0gIndoaXRlIiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChzdGF0ID0gInN0cmF0dW0iLCBhZXMobGFiZWwgPSBhZnRlcl9zdGF0KHN0cmF0dW0pKSwgc2l6ZSA9IDYpICsNCiAgbGFicyh4PSAiVmFyaWFibGVzIiwgeSA9ICJGcmVxdWVuY3kiLCBmaWxsID0gIkpvdXJuYWwgQ2F0ZWdvcnkgQWxsb2NhdGVkIikgKw0KICB0aGVtZV9zdXBwbCgpDQoNCmZpZ3M2DQoNCiBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzNi5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczYuanBnIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KDQogIA0KYGBgDQoNCiMjIEZpZ3VyZSBzNyANCkEgYmFyIHBsb3Qgc2hvd2luZyB0aGUgcGVyY2VudGFnZSBhbmQgdG90YWwgY291bnQgb2YgZWZmZWN0IHNpemUgY2FsY3VsYXRpb24gdHlwZSB1c2VkIGluIG1ldGEtYW5hbHlzaXMgaW52ZXN0aWdhdGluZyB0aGUgaW1wYWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiBOb3RlOiBzb21lIG1ldGEtYW5hbHlzaXMgbWF5IGNvbnRyaWJ1dGUgdG8gbXVsdGlwbGUgc2VjdGlvbnMgaWYgdGhlIHN0dWR5IGludm9sdmVzIG11bHRpcGxlIGVmZmVjdCBzaXplIGNhbGN1bGF0aW9ucy4g4oCcT3RoZXIgZWZmZWN0IHNpemVz4oCdIGlzIGFsbCBvdGhlciBlZmZlY3Qgc2l6ZXMgd2l0aCBhIGNvdW50IGxlc3MgdGhhbiBvciBlcXVhbCB0byAyDQpgYGB7ciwgZmlnLndpZHRoPTE2LCBmaWcuaGVpZ2h0PTEwfQ0KIyBDYWxjdWxhdGUgdGhlIHRvdGFsIGNvdW50IGZvciBlYWNoIGNhdGVnb3J5DQplZmZlY3RzaXplX2NvdW50IDwtIHNkICU+JSANCiAgc2VwYXJhdGVfcm93cyhlZmZlY3Rfc2l6ZSwgc2VwID0gIixcXHMrIikgJT4lIA0KICBjb3VudChlZmZlY3Rfc2l6ZSkgJT4lDQogIGZpbHRlcihlZmZlY3Rfc2l6ZSAhPSAiTkEiKSAlPiUNCiAgbXV0YXRlKGVmZmVjdF9zaXplID0gaWZlbHNlKG48PSAyLCAiT3RoZXIgZWZmZWN0IHNpemVzIiwgYXMuY2hhcmFjdGVyKGVmZmVjdF9zaXplKSkpICU+JSANCiAgZ3JvdXBfYnkoZWZmZWN0X3NpemUpICU+JQ0KICBzdW1tYXJpc2UobiA9IHN1bShuKSkNCg0KIyBDYWxjdWxhdGUgcHJvcG9ydGlvbiBhbmQgcGVyY2VudGFnZSBmb3IgZWFjaCBjYXRlZ29yeQ0KZWZmZWN0c2l6ZV9wY3QgPC0gZWZmZWN0c2l6ZV9jb3VudCAlPiUNCiAgbXV0YXRlKHByb3BvcnRpb24gPSBuIC8gc3VtKGVmZmVjdHNpemVfY291bnQkbiksDQogICAgICAgICBwZXJjZW50YWdlID0gcHJvcG9ydGlvbiAqIDEwMCkNCg0KIyBDcmVhdGUgdGhlIGNvdW50IHBsb3QNCmZpZ3M3IDwtICBlZmZlY3RzaXplX2NvdW50ICU+JQ0KICBnZ3Bsb3QoYWVzKHggPSBuLCB5ID0gcmVvcmRlcihlZmZlY3Rfc2l6ZSwgbiksIGZpbGwgPSAiIzFiOWU3NyIpKSArDQogIGdlb21fYmFyKHN0YXQgPSAiaWRlbnRpdHkiLCB3aWR0aCA9IDAuOCAsIGFscGhhID0gMC43KSArDQogIGdlb21fdGV4dChhZXMobGFiZWwgPSBuLCB4ID0gbiAvIDIsIHkgPSByZW9yZGVyKGVmZmVjdF9zaXplLCBuKSksIGhqdXN0ID0gMC41LCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChkYXRhID0gZWZmZWN0c2l6ZV9wY3QsIGFlcyhsYWJlbCA9IHBhc3RlMCgiKCIsIHJvdW5kKHBlcmNlbnRhZ2UsIDEpLCAiJSkiKSwgeCA9IG4pLCANCiAgICAgICAgICAgIGhqdXN0ID0gLTAuMSwgc2l6ZSA9IDYsIGNvbG9yID0gImJsYWNrIiwgZm9udGZhY2UgPSAiYm9sZCIpICsNCiAgc2NhbGVfZmlsbF9pZGVudGl0eShndWlkZSA9ICJub25lIikgKw0KICBzY2FsZV94X2NvbnRpbnVvdXMobmFtZSA9ICJBcnRpY2xlIENvdW50IiwgZXhwYW5kID0gYygwLCAwKSwgbGltaXRzID0gYygwLCBtYXgoZWZmZWN0c2l6ZV9jb3VudCRuKSoxLjEpKSArDQogIGxhYnMoeSA9IE5VTEwpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzNw0KDQogIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3M3LnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczcuanBnIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KYGBgDQoNCiMjIEZpZ3VyZSBzOA0KQW4gYWxsdXZpYWwgcGxvdCBzaG93aW5nIHRoZSByZWxhdGlvbnNoaXAgYmV0d2VlbiB0aGUgSm91cm5hbCBDaXRhdGlvbiBSZXBvcnQgQ2F0ZWdvcnkgYW5kIHRoZSBlZmZlY3Qgc2l6ZSB1c2VkLiANCmBgYHtyLCBmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIERhdGEgVHJhbnNmb3JtYXRpb24gDQplZmZlY3RzaXplX2FsbHV2aWFsIDwtIHNkICU+JSANCiAgICBzZXBhcmF0ZV9yb3dzKGVmZmVjdF9zaXplLCBzZXAgPSAiLFxccysiKSAlPiUNCiAgICBzZXBhcmF0ZV9yb3dzKEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBzZXAgPSAiL1xccysiKSAlPiUgDQogICAgZmlsdGVyKCFncmVwbCgibm8gY2F0ZWdvcnkgZm91bmQiLCBKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgaWdub3JlLmNhc2UgPSBUUlVFKSkgJT4lIA0KICAgIGZpbHRlcighaXMubmEoZWZmZWN0X3NpemUpKSAlPiUNCiAgICBncm91cF9ieShKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgZWZmZWN0X3NpemUpICU+JSANCiAgICBjb3VudChlZmZlY3Rfc2l6ZSwgSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpICU+JSANCiAgICBzdW1tYXJpc2UoZnJlcSA9IG4oKSwgLmdyb3VwcyA9ICdkcm9wJykgJT4lIA0KICAgIGdyb3VwX2J5KGVmZmVjdF9zaXplKSANCg0KDQojIENyZWF0ZSB0aGUgQWxsdXZpYWwgcGxvdA0KZmlnczggPC0gZWZmZWN0c2l6ZV9hbGx1dmlhbCAlPiUgDQpnZ3Bsb3QoYWVzKHkgPSBmcmVxICxheGlzMSA9IEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBheGlzMiA9IGVmZmVjdF9zaXplKSkgKw0KICBzY2FsZV94X2Rpc2NyZXRlKGxpbWl0cyA9IGMoIkpvdXJuYWwgQ2F0ZWdvcnkiLCAiRWZmZWN0IFNpemUiKSwgZXhwYW5kID0gYyguMDUsIC4wNSkpICsNCiAgeGxhYigiVmFyaWFibGVzIikgKw0KICBnZW9tX2FsbHV2aXVtKGFlcyhmaWxsID0gSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpKSArDQogIGdlb21fc3RyYXR1bSh3aWR0aCA9IDEvNC41LCBmaWxsID0gIndoaXRlIiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChzdGF0ID0gInN0cmF0dW0iLCBhZXMobGFiZWwgPSBhZnRlcl9zdGF0KHN0cmF0dW0pKSwgc2l6ZSA9IDYpICsNCiAgdGhlbWVfbWluaW1hbCgpICsNCiAgbGFicyh4PSAiVmFyaWFibGVzIiwgeSA9ICJGcmVxdWVuY3kiLCBmaWxsID0gIkpvdXJuYWwgQ2F0ZWdvcnkgQWxsb2NhdGVkIikgKw0KICB0aGVtZV9zdXBwbCgpDQogIA0KZmlnczgNCg0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3M4LnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzOC5qcGciKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQpgYGANCg0KIyMgRmlndXJlIHM5DQpBIGJhciBwbG90IHNob3dpbmcgdGhlIHBlcmNlbnRhZ2UgYW5kIHRvdGFsIGNvdW50IG9mIHNvZnR3YXJlIGZvciBhbmFseXNpcyBpbiBtZXRhLWFuYWx5c2lzIGludmVzdGlnYXRpbmcgdGhlIGltcGFjdHMgb2Ygb3JnYW5vY2hsb3JpbmUgcGVzdGljaWRlcy4gTm90ZTogc29tZSBtZXRhLWFuYWx5c2lzIG1heSBjb250cmlidXRlIHRvIG11bHRpcGxlIHNlY3Rpb25zIGlmIHRoZSBzdHVkeSBpbnZvbHZlcyBtdWx0aXBsZSBzb2Z0d2FyZXMgDQpgYGB7ciwgZmlnLndpZHRoPTE2LCBmaWcuaGVpZ2h0PTEwfQ0KIyBDYWxjdWxhdGUgdGhlIHRvdGFsIGNvdW50IGZvciBlYWNoIGNhdGVnb3J5DQpzb2Z0d2FyZV9jb3VudCA8LSBzZCAlPiUNCiAgc2VwYXJhdGVfcm93cyhzb2Z0d2FyZV9hbmFseXNpcywgc2VwID0gIixcXHMrIikgJT4lDQogIG11dGF0ZShzb2Z0d2FyZV9hbmFseXNpcyA9IGlmZWxzZShncmVwbCgiY29tcHJlaGVuc2l2ZSBtZXRhLWFuYWx5c2lzIiwgc29mdHdhcmVfYW5hbHlzaXMpLCAiQ01BUyIsIHNvZnR3YXJlX2FuYWx5c2lzKSkgJT4lDQogIG11dGF0ZShzb2Z0d2FyZV9hbmFseXNpcyA9IGlmZWxzZShncmVwbCgibm90IHJlcG9ydGVkIiwgc29mdHdhcmVfYW5hbHlzaXMpLCAibm8gc29mdHdhcmUgcmVwb3J0ZWQiLCBzb2Z0d2FyZV9hbmFseXNpcykpICAlPiUgDQogIGNvdW50KHNvZnR3YXJlX2FuYWx5c2lzKSAlPiUNCiAgZmlsdGVyKHNvZnR3YXJlX2FuYWx5c2lzICE9ICJOQSIpICU+JQ0KICBncm91cF9ieShzb2Z0d2FyZV9hbmFseXNpcykgJT4lDQogIHN1bW1hcmlzZShuID0gc3VtKG4pKQ0KDQoNCiMgQ2FsY3VsYXRlIHByb3BvcnRpb24gYW5kIHBlcmNlbnRhZ2UgZm9yIGVhY2ggY2F0ZWdvcnkNCnNvZnR3YXJlX3BjdCA8LSBzb2Z0d2FyZV9jb3VudCAlPiUNCiAgbXV0YXRlKHByb3BvcnRpb24gPSBuIC8gc3VtKHNvZnR3YXJlX2NvdW50JG4pLA0KICAgICAgICAgcGVyY2VudGFnZSA9IHByb3BvcnRpb24gKiAxMDApDQoNCiMgQ3JlYXRlIHRoZSBjb3VudCBwbG90DQpmaWdzOSA8LSBzb2Z0d2FyZV9jb3VudCAlPiUNCiAgZ2dwbG90KGFlcyh4ID0gbiwgeSA9IHJlb3JkZXIoc29mdHdhcmVfYW5hbHlzaXMsIG4pLCBmaWxsID0gIiMxYjllNzciKSkgKw0KICBnZW9tX2JhcihzdGF0ID0gImlkZW50aXR5Iiwgd2lkdGggPSAwLjggLCBhbHBoYSA9IDAuNykgKw0KICBnZW9tX3RleHQoYWVzKGxhYmVsID0gbiwgeCA9IG4gLyAyLCB5ID0gcmVvcmRlcihzb2Z0d2FyZV9hbmFseXNpcywgbikpLCBoanVzdCA9IDAuNSwgc2l6ZSA9IDYsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoZGF0YSA9IHNvZnR3YXJlX3BjdCwgYWVzKGxhYmVsID0gcGFzdGUwKCIoIiwgcm91bmQocGVyY2VudGFnZSwgMSksICIlKSIpLCB4ID0gbiksIA0KICAgICAgICAgICAgaGp1c3QgPSAtMC4xLCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siLCBmb250ZmFjZSA9ICJib2xkIikgKw0KICBzY2FsZV9maWxsX2lkZW50aXR5KGd1aWRlID0gIm5vbmUiKSArDQogIHNjYWxlX3hfY29udGludW91cyhuYW1lID0gIkFydGljbGUgQ291bnQiLCBleHBhbmQgPSBjKDAsIDApLCBsaW1pdHMgPSBjKDAsIG1heChzb2Z0d2FyZV9jb3VudCRuKSoxLjEpKSArDQogIGxhYnMoeSA9IE5VTEwpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzOQ0KDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczkucGRmIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3M5LmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KYGBgDQoNCiMjIEZpZ3VyZSBzMTAgDQpBbiBhbGx1dmlhbCBwbG90IHNob3dpbmcgdGhlIHJlbGF0aW9uc2hpcCBiZXR3ZWVuIHRoZSBKb3VybmFsIENpdGF0aW9uIFJlcG9ydCBDYXRlZ29yeSBhbmQgdGhlIHNvZnR3YXJlIHVzZWQgZm9yIGFuYWx5c2lzLiANCmBgYHtyLCBmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIERhdGEgVHJhbnNmb3JtYXRpb24gDQpzb2Z0d2FyZV9hbmFseXNpc19hbGx1dmlhbCA8LSBzZCAlPiUgDQogICAgc2VwYXJhdGVfcm93cyhzb2Z0d2FyZV9hbmFseXNpcywgc2VwID0gIixcXHMrIikgJT4lDQogICAgc2VwYXJhdGVfcm93cyhKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgc2VwID0gIi9cXHMrIikgJT4lIA0KICBtdXRhdGUoc29mdHdhcmVfYW5hbHlzaXMgPSBpZmVsc2UoZ3JlcGwoImNvbXByZWhlbnNpdmUgbWV0YS1hbmFseXNpcyIsIHNvZnR3YXJlX2FuYWx5c2lzKSwgIkNNQVMiLCBzb2Z0d2FyZV9hbmFseXNpcykpICU+JQ0KICBtdXRhdGUoc29mdHdhcmVfYW5hbHlzaXMgPSBpZmVsc2UoZ3JlcGwoIm5vdCByZXBvcnRlZCIsIHNvZnR3YXJlX2FuYWx5c2lzKSwgIm5vIHNvZnR3YXJlIHJlcG9ydGVkIiwgc29mdHdhcmVfYW5hbHlzaXMpKSAgJT4lIA0KICAgIGZpbHRlcighaXMubmEoc29mdHdhcmVfYW5hbHlzaXMpKSAlPiUNCiAgICBncm91cF9ieShKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgc29mdHdhcmVfYW5hbHlzaXMpICU+JSANCiAgICBjb3VudChzb2Z0d2FyZV9hbmFseXNpcywgSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpICU+JSANCiAgICBzdW1tYXJpc2UoZnJlcSA9IG4oKSwgLmdyb3VwcyA9ICdkcm9wJykgJT4lIA0KICAgIGdyb3VwX2J5KHNvZnR3YXJlX2FuYWx5c2lzKQ0KDQojIENyZWF0ZSB0aGUgQWxsdXZpYWwgcGxvdCBmb3IgU29mdHdhcmUgQW5hbHlzaXMNCmZpZ3MxMCA8LSBzb2Z0d2FyZV9hbmFseXNpc19hbGx1dmlhbCAlPiUgDQpnZ3Bsb3QoYWVzKHkgPSBmcmVxICxheGlzMSA9IEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBheGlzMiA9IHNvZnR3YXJlX2FuYWx5c2lzKSkgKw0KICBzY2FsZV94X2Rpc2NyZXRlKGxpbWl0cyA9IGMoIkpvdXJuYWwgQ2F0ZWdvcnkiLCAiU29mdHdhcmUgQW5hbHlzaXMiKSwgZXhwYW5kID0gYyguMDUsIC4wNSkpICsNCiAgeGxhYigiVmFyaWFibGVzIikgKw0KICBnZW9tX2FsbHV2aXVtKGFlcyhmaWxsID0gSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpKSArDQogIGdlb21fc3RyYXR1bSh3aWR0aCA9IDEvNCwgZmlsbCA9ICJ3aGl0ZSIsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoc3RhdCA9ICJzdHJhdHVtIiwgYWVzKGxhYmVsID0gYWZ0ZXJfc3RhdChzdHJhdHVtKSksIHNpemUgPSA2KSArDQogIGxhYnMoeD0gIlZhcmlhYmxlcyIsIHkgPSAiRnJlcXVlbmN5IiwgZmlsbCA9ICJKb3VybmFsIENhdGVnb3J5IEFsbG9jYXRlZCIpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzMTANCg0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MxMC5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczEwLmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KYGBgDQoNCiMjIEZpZ3VyZSBzMTENCkEgYmFyIHBsb3Qgc2hvd2luZyB0aGUgcGVyY2VudGFnZSBhbmQgdG90YWwgY291bnQgb2YgaGV0ZXJvZ2VuZWl0eSBhc3Nlc3NtZW50IGluIG1ldGEtYW5hbHlzaXMgaW52ZXN0aWdhdGluZyB0aGUgaW1wYWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiBOb3RlOiBzb21lIG1ldGEtYW5hbHlzaXMgbWF5IGNvbnRyaWJ1dGUgdG8gbXVsdGlwbGUgc2VjdGlvbnMgaWYgdGhlIHN0dWR5IGludm9sdmVzIG11bHRpcGxlIGhldGVyb2dlbmVpdHkgYXNzZXNzbWVudHMgDQpgYGB7ciwgZmlnLndpZHRoPTE2LCBmaWcuaGVpZ2h0PTEwfQ0KIyBDYWxjdWxhdGUgdGhlIHRvdGFsIGNvdW50IGZvciBlYWNoIGNhdGVnb3J5DQpoZXRlcm9nZW5laXR5X2NvdW50IDwtIHNkICU+JSANCiAgc2VwYXJhdGVfcm93cyhoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kLCBzZXAgPSAiLFxccysiKSAlPiUgDQogIGNvdW50KGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QpICU+JQ0KICAgIG11dGF0ZShoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kID0gaWZlbHNlKGdyZXBsKCJub3QgcmVwb3J0ZWQiLCBoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kKSwgIm5vIGhldGVyb2dlbmVpdHlcbm1lYXN1cmUgcmVwb3J0ZWQiLCBoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kKSkgICU+JSANCiAgZmlsdGVyKGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QgIT0gIk5BIikgJT4lDQogICAgZ3JvdXBfYnkoaGV0ZXJvZ2VuZWl0eV9hc3Nlc3NtZW50X21ldGhvZCkgJT4lDQogIHN1bW1hcmlzZShuID0gc3VtKG4pKQ0KDQojIENhbGN1bGF0ZSBwcm9wb3J0aW9uIGFuZCBwZXJjZW50YWdlIGZvciBlYWNoIGNhdGVnb3J5DQpoZXRlcm9nZW5laXR5X3BjdCA8LSBoZXRlcm9nZW5laXR5X2NvdW50ICU+JQ0KICBtdXRhdGUocHJvcG9ydGlvbiA9IG4gLyBzdW0oaGV0ZXJvZ2VuZWl0eV9jb3VudCRuKSwNCiAgICAgICAgIHBlcmNlbnRhZ2UgPSBwcm9wb3J0aW9uICogMTAwKQ0KDQojIENyZWF0ZSB0aGUgY291bnQgcGxvdA0KZmlnczExIDwtIGhldGVyb2dlbmVpdHlfY291bnQgJT4lDQogIGdncGxvdChhZXMoeCA9IG4sIHkgPSByZW9yZGVyKGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QsIG4pLCBmaWxsID0gIiMxYjllNzciKSkgKw0KICBnZW9tX2JhcihzdGF0ID0gImlkZW50aXR5Iiwgd2lkdGggPSAwLjggLCBhbHBoYSA9IDAuNykgKw0KICBnZW9tX3RleHQoYWVzKGxhYmVsID0gbiwgeCA9IG4gLyAyLCB5ID0gcmVvcmRlcihoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kLCBuKSksIGhqdXN0ID0gMC41LCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChkYXRhID0gaGV0ZXJvZ2VuZWl0eV9wY3QsIGFlcyhsYWJlbCA9IHBhc3RlMCgiKCIsIHJvdW5kKHBlcmNlbnRhZ2UsIDEpLCAiJSkiKSwgeCA9IG4pLCANCiAgICAgICAgICAgIGhqdXN0ID0gLTAuMSwgc2l6ZSA9IDYsIGNvbG9yID0gImJsYWNrIiwgZm9udGZhY2UgPSAiYm9sZCIpICsNCiAgc2NhbGVfZmlsbF9pZGVudGl0eShndWlkZSA9ICJub25lIikgKw0KICBzY2FsZV94X2NvbnRpbnVvdXMobmFtZSA9ICJBcnRpY2xlIENvdW50IiwgZXhwYW5kID0gYygwLCAwKSwgbGltaXRzID0gYygwLCBtYXgoaGV0ZXJvZ2VuZWl0eV9jb3VudCRuKSoxLjEpKSArDQogIGxhYnMoeSA9IE5VTEwpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzMTENCg0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MxMS5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczExLmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KYGBgDQogDQojIyBGaWd1cmUgczEyIA0KQW4gYWxsdXZpYWwgcGxvdCBzaG93aW5nIHRoZSByZWxhdGlvbnNoaXAgYmV0d2VlbiB0aGUgSm91cm5hbCBDaXRhdGlvbiBSZXBvcnQgQ2F0ZWdvcnkgYW5kIGhldGVyb2dlbmVpdHkgYXNzZXNzbWVudCANCmBgYHtyLCBmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIERhdGEgVHJhbnNmb3JtYXRpb24gDQpoZXRlcm9nZW5laXR5X2FsbHV2aWFsIDwtIHNkICU+JSANCiAgICBzZXBhcmF0ZV9yb3dzKGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QsIHNlcCA9ICIsXFxzKyIpICU+JQ0KICAgIHNlcGFyYXRlX3Jvd3MoSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQsIHNlcCA9ICIvXFxzKyIpICU+JSANCiAgbXV0YXRlKGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QgPSBpZmVsc2UoZ3JlcGwoIm5vdCByZXBvcnRlZCIsIGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QpLCAibm8gaGV0ZXJvZ2VuZWl0eVxubWVhc3VyZSByZXBvcnRlZCIsIGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QpKSAgJT4lIA0KICAgIGZpbHRlcighaXMubmEoaGV0ZXJvZ2VuZWl0eV9hc3Nlc3NtZW50X21ldGhvZCkpICU+JQ0KICAgIGdyb3VwX2J5KEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kKSAlPiUgDQogICAgY291bnQoaGV0ZXJvZ2VuZWl0eV9hc3Nlc3NtZW50X21ldGhvZCwgSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpICU+JSANCiAgICBzdW1tYXJpc2UoZnJlcSA9IG4oKSwgLmdyb3VwcyA9ICdkcm9wJykgJT4lIA0KICAgIGdyb3VwX2J5KGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QpIA0KDQojIENyZWF0ZSB0aGUgQWxsdXZpYWwgcGxvdA0KZmlnczEyIDwtIGhldGVyb2dlbmVpdHlfYWxsdXZpYWwgJT4lIA0KZ2dwbG90KGFlcyh5ID0gZnJlcSAsYXhpczEgPSBKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgYXhpczIgPSBoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kKSkgKw0KICBzY2FsZV94X2Rpc2NyZXRlKGxpbWl0cyA9IGMoIkpvdXJuYWwgQ2l0YXRpb24gUmVwb3J0IENhdGVnb3J5IiwgIkhldGVyb2dlbmVpdHkiKSwgZXhwYW5kID0gYyguMDUsIC4wNSkpICsNCiAgeGxhYigiVmFyaWFibGVzIikgKw0KICBnZW9tX2FsbHV2aXVtKGFlcyhmaWxsID0gSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpKSArDQogIGdlb21fc3RyYXR1bSh3aWR0aCA9IDEvNC41LCBmaWxsID0gIndoaXRlIiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChzdGF0ID0gInN0cmF0dW0iLCBhZXMobGFiZWwgPSBhZnRlcl9zdGF0KHN0cmF0dW0pKSwgc2l6ZSA9IDYpICsNCiAgbGFicyh4PSAiVmFyaWFibGVzIiwgeSA9ICJGcmVxdWVuY3kiLCBmaWxsID0gIkpvdXJuYWwgQ2F0ZWdvcnkgQWxsb2NhdGVkIikgKw0KICB0aGVtZV9zdXBwbCgpDQoNCmZpZ3MxMg0KDQogIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MxMi5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MxMi5qcGciKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQpgYGANCiANCiMjIEZpZ3VyZSBzMTMNCkEgYmFyIHBsb3Qgc2hvd2luZyB0aGUgcGVyY2VudGFnZSBhbmQgdG90YWwgY291bnQgb2Ygc2Vuc2l0aXZpdHkgYW5hbHlzaXMgaW4gbWV0YS1hbmFseXNpcyBpbnZlc3RpZ2F0aW5nIHRoZSBpbXBhY3RzIG9mIG9yZ2Fub2NobG9yaW5lIHBlc3RpY2lkZXMuIE5vdGU6IHNvbWUgbWV0YS1hbmFseXNpcyBtYXkgY29udHJpYnV0ZSB0byBtdWx0aXBsZSBzZWN0aW9ucyBpZiB0aGUgc3R1ZHkgaW52b2x2ZXMgbXVsdGlwbGUgc2Vuc2l0aXZpdHkgYW5hbHlzZXMgYXJlIGNvbXBsZXRlZA0KYGBge3IsIGZpZy53aWR0aD0xNiwgZmlnLmhlaWdodD0xMH0NCiMgQ2FsY3VsYXRlIHRoZSB0b3RhbCBjb3VudCBmb3IgZWFjaCBjYXRlZ29yeQ0Kc2Vuc2l0aXZpdHlfY291bnQgPC0gc2QgJT4lIA0KICBzZXBhcmF0ZV9yb3dzKHNlbnNpdGl2aXR5X2FuYWx5c2lzX21ldGhvZCwgc2VwID0gIixcXHMrIikgJT4lIA0KICBjb3VudChzZW5zaXRpdml0eV9hbmFseXNpc19tZXRob2QpICU+JQ0KICBmaWx0ZXIoc2Vuc2l0aXZpdHlfYW5hbHlzaXNfbWV0aG9kICE9ICJOQSIpICU+JSAgIA0KICBncm91cF9ieShzZW5zaXRpdml0eV9hbmFseXNpc19tZXRob2QpICU+JQ0KICBzdW1tYXJpc2UobiA9IHN1bShuKSkNCg0KIyBDYWxjdWxhdGUgcHJvcG9ydGlvbiBhbmQgcGVyY2VudGFnZSBmb3IgZWFjaCBjYXRlZ29yeQ0Kc2Vuc2l0aXZpdHlfcGN0IDwtIHNlbnNpdGl2aXR5X2NvdW50ICU+JQ0KICBtdXRhdGUocHJvcG9ydGlvbiA9IG4gLyBzdW0oc2Vuc2l0aXZpdHlfY291bnQkbiksDQogICAgICAgICBwZXJjZW50YWdlID0gcHJvcG9ydGlvbiAqIDEwMCkNCg0KIyBDcmVhdGUgdGhlIGNvdW50IHBsb3QNCmZpZ3MxMyA8LSBzZW5zaXRpdml0eV9jb3VudCAlPiUNCiAgZ2dwbG90KGFlcyh4ID0gbiwgeSA9IHJlb3JkZXIoc2Vuc2l0aXZpdHlfYW5hbHlzaXNfbWV0aG9kLCBuKSwgZmlsbCA9ICIjMWI5ZTc3IikpICsNCiAgZ2VvbV9iYXIoc3RhdCA9ICJpZGVudGl0eSIsIHdpZHRoID0gMC44ICwgYWxwaGEgPSAwLjcpICsNCiAgZ2VvbV90ZXh0KGFlcyhsYWJlbCA9IG4sIHggPSBuIC8gMiwgeSA9IHJlb3JkZXIoc2Vuc2l0aXZpdHlfYW5hbHlzaXNfbWV0aG9kLCBuKSksIGhqdXN0ID0gMC41LCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChkYXRhID0gc2Vuc2l0aXZpdHlfcGN0LCBhZXMobGFiZWwgPSBwYXN0ZTAoIigiLCByb3VuZChwZXJjZW50YWdlLCAxKSwgIiUpIiksIHggPSBuKSwgDQogICAgICAgICAgICBoanVzdCA9IC0wLjEsIHNpemUgPSA2LCBjb2xvciA9ICJibGFjayIsIGZvbnRmYWNlID0gImJvbGQiKSArDQogIHNjYWxlX2ZpbGxfaWRlbnRpdHkoZ3VpZGUgPSAibm9uZSIpICsNCiAgc2NhbGVfeF9jb250aW51b3VzKG5hbWUgPSAiQXJ0aWNsZSBDb3VudCIsIGV4cGFuZCA9IGMoMCwgMCksIGxpbWl0cyA9IGMoMCwgbWF4KHNlbnNpdGl2aXR5X2NvdW50JG4pKjEuMSkpICsNCiAgbGFicyh5ID0gTlVMTCkgKw0KIHRoZW1lX3N1cHBsKCkNCg0KZmlnczEzDQoNCiAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczEzLnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczEzLmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KYGBgDQoNCiMjIEZpZ3VyZSBzMTQNCkFuIGFsbHV2aWFsIHBsb3Qgc2hvd2luZyB0aGUgcmVsYXRpb25zaGlwIGJldHdlZW4gdGhlIEpvdXJuYWwgQ2l0YXRpb24gUmVwb3J0IENhdGVnb3J5IGFuZCBzZW5zaXRpdml0eSBhbmFseXNpcyANCmBgYHtyLCBmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIERhdGEgVHJhbnNmb3JtYXRpb24gDQpzZW5zaXRpdml0eV9hbmFseXNpc19hbGx1dmlhbCA8LSBzZCAlPiUgDQogICAgc2VwYXJhdGVfcm93cyhzZW5zaXRpdml0eV9hbmFseXNpc19tZXRob2QsIHNlcCA9ICIsXFxzKyIpICU+JQ0KICAgIHNlcGFyYXRlX3Jvd3MoSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQsIHNlcCA9ICIvXFxzKyIpICU+JSANCiAgICBmaWx0ZXIoIWlzLm5hKHNlbnNpdGl2aXR5X2FuYWx5c2lzX21ldGhvZCkpICU+JQ0KICAgIGdyb3VwX2J5KEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBzZW5zaXRpdml0eV9hbmFseXNpc19tZXRob2QpICU+JSANCiAgICBjb3VudChzZW5zaXRpdml0eV9hbmFseXNpc19tZXRob2QsIEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkKSAlPiUgDQogICAgc3VtbWFyaXNlKGZyZXEgPSBuKCksIC5ncm91cHMgPSAnZHJvcCcpICU+JSANCiAgICBncm91cF9ieShzZW5zaXRpdml0eV9hbmFseXNpc19tZXRob2QpDQoNCiMgQ3JlYXRlIHRoZSBBbGx1dmlhbCBwbG90DQpmaWdzMTQgPC0gc2Vuc2l0aXZpdHlfYW5hbHlzaXNfYWxsdXZpYWwgJT4lIA0KZ2dwbG90KGFlcyh5ID0gZnJlcSAsYXhpczEgPSBKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgYXhpczIgPSBzZW5zaXRpdml0eV9hbmFseXNpc19tZXRob2QpKSArDQogIHNjYWxlX3hfZGlzY3JldGUobGltaXRzID0gYygiSm91cm5hbCBDaXRhdGlvbiBSZXBvcnQgQ2F0ZWdvcnkiLCAiU2Vuc2l0aXZpdHkgQW5hbHlzaXMgTWV0aG9kIiksIGV4cGFuZCA9IGMoLjA1LCAuMDUpKSArDQogIHhsYWIoIlZhcmlhYmxlcyIpICsNCiAgZ2VvbV9hbGx1dml1bShhZXMoZmlsbCA9IEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkKSkgKw0KICBnZW9tX3N0cmF0dW0od2lkdGggPSAxLzQuNSwgZmlsbCA9ICJ3aGl0ZSIsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoc3RhdCA9ICJzdHJhdHVtIiwgYWVzKGxhYmVsID0gYWZ0ZXJfc3RhdChzdHJhdHVtKSksIHNpemUgPSA2KSArDQogIGxhYnMoeD0gIlZhcmlhYmxlcyIsIHkgPSAiRnJlcXVlbmN5IiwgZmlsbCA9ICJKb3VybmFsIENhdGVnb3J5IEFsbG9jYXRlZCIpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzMTQNCg0KICBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMTQucGRmIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KICBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMTQuanBnIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KDQpgYGANCg0KIyMgRmlndXJlIHMxNSANCkEgYmFyIHBsb3Qgc2hvd2luZyB0aGUgcGVyY2VudGFnZSBhbmQgdG90YWwgY291bnQgb2YgYmlhcyB0eXBlIGFzc2Vzc2VkIGluIG1ldGEtYW5hbHlzaXMgaW52ZXN0aWdhdGluZyB0aGUgaW1wYWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiBOb3RlOiBzb21lIG1ldGEtYW5hbHlzaXMgbWF5IGNvbnRyaWJ1dGUgdG8gbXVsdGlwbGUgc2VjdGlvbnMgaWYgdGhlIHN0dWR5IGludm9sdmVzIG11bHRpcGxlIGJpYXMgdHlwZXMgYXJlIGFzc2Vzc2VkIA0KYGBge3IsIGZpZy53aWR0aD0xNiwgZmlnLmhlaWdodD0xMH0NCiMgQ2FsY3VsYXRlIHRoZSB0b3RhbCBjb3VudCBmb3IgZWFjaCBjYXRlZ29yeQ0KYmlhc190eXBlX2NvdW50IDwtIHNkICU+JSANCiAgc2VwYXJhdGVfcm93cyhiaWFzX2Fzc2Vzc21lbnRfdHlwZSwgc2VwID0gIixcXHMrIikgJT4lIA0KICBjb3VudChiaWFzX2Fzc2Vzc21lbnRfdHlwZSkgJT4lDQogIGZpbHRlcihiaWFzX2Fzc2Vzc21lbnRfdHlwZSAhPSAiTkEiKSAlPiUNCiAgZ3JvdXBfYnkoYmlhc19hc3Nlc3NtZW50X3R5cGUpICU+JQ0KICBzdW1tYXJpc2UobiA9IHN1bShuKSkNCg0KIyBDYWxjdWxhdGUgcHJvcG9ydGlvbiBhbmQgcGVyY2VudGFnZSBmb3IgZWFjaCBjYXRlZ29yeQ0KYmlhc190eXBlX3BjdCA8LSBiaWFzX3R5cGVfY291bnQgJT4lDQogIG11dGF0ZShwcm9wb3J0aW9uID0gbiAvIHN1bShiaWFzX3R5cGVfY291bnQkbiksDQogICAgICAgICBwZXJjZW50YWdlID0gcHJvcG9ydGlvbiAqIDEwMCkNCg0KIyBDcmVhdGUgdGhlIGNvdW50IHBsb3QNCmZpZ3MxNSA8LSBiaWFzX3R5cGVfY291bnQgJT4lDQogIGdncGxvdChhZXMoeCA9IG4sIHkgPSByZW9yZGVyKGJpYXNfYXNzZXNzbWVudF90eXBlLCBuKSwgZmlsbCA9ICIjMWI5ZTc3IikpICsNCiAgZ2VvbV9iYXIoc3RhdCA9ICJpZGVudGl0eSIsIHdpZHRoID0gMC44ICwgYWxwaGEgPSAwLjcpICsNCiAgZ2VvbV90ZXh0KGFlcyhsYWJlbCA9IG4sIHggPSBuIC8gMiwgeSA9IHJlb3JkZXIoYmlhc19hc3Nlc3NtZW50X3R5cGUsIG4pKSwgaGp1c3QgPSAwLjUsIHNpemUgPSA2LCBjb2xvciA9ICJibGFjayIpICsNCiAgZ2VvbV90ZXh0KGRhdGEgPSBiaWFzX3R5cGVfcGN0LCBhZXMobGFiZWwgPSBwYXN0ZTAoIigiLCByb3VuZChwZXJjZW50YWdlLCAxKSwgIiUpIiksIHggPSBuKSwgDQogICAgICAgICAgICBoanVzdCA9IC0wLjEsIHNpemUgPSA2LCBjb2xvciA9ICJibGFjayIsIGZvbnRmYWNlID0gImJvbGQiKSArDQogIHNjYWxlX2ZpbGxfaWRlbnRpdHkoZ3VpZGUgPSAibm9uZSIpICsNCiAgc2NhbGVfeF9jb250aW51b3VzKG5hbWUgPSAiQXJ0aWNsZSBDb3VudCIsIGV4cGFuZCA9IGMoMCwgMCksIGxpbWl0cyA9IGMoMCwgbWF4KGJpYXNfdHlwZV9jb3VudCRuKSoxLjEpKSArDQogIGxhYnMoeSA9IE5VTEwpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzMTUNCg0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MxNS5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczE1LmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KYGBgDQoNCiMjIEZpZ3VyZSBzMTYNCkFuIGFsbHV2aWFsIHBsb3Qgc2hvd2luZyB0aGUgcmVsYXRpb25zaGlwIGJldHdlZW4gdGhlIEpvdXJuYWwgQ2l0YXRpb24gUmVwb3J0IENhdGVnb3J5IGFuZCBiaWFzIGFzc2Vzc21lbnQgdHlwZQ0KYGBge3IsIGZpZy53aWR0aD0xNiwgZmlnLmhlaWdodD0xMH0NCiMgRGF0YSBUcmFuc2Zvcm1hdGlvbiANCmJpYXNfYXNzZXNzbWVudF9hbGx1dmlhbCA8LSBzZCAlPiUgDQogICAgc2VwYXJhdGVfcm93cyhiaWFzX2Fzc2Vzc21lbnRfdHlwZSwgc2VwID0gIixcXHMrIikgJT4lDQogICAgc2VwYXJhdGVfcm93cyhKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgc2VwID0gIi9cXHMrIikgJT4lIA0KICAgIGZpbHRlcighaXMubmEoYmlhc19hc3Nlc3NtZW50X3R5cGUpKSAlPiUNCiAgICBncm91cF9ieShKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgYmlhc19hc3Nlc3NtZW50X3R5cGUpICU+JSANCiAgICBjb3VudChiaWFzX2Fzc2Vzc21lbnRfdHlwZSwgSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpICU+JSANCiAgICBzdW1tYXJpc2UoZnJlcSA9IG4oKSwgLmdyb3VwcyA9ICdkcm9wJykgJT4lIA0KICAgIGdyb3VwX2J5KGJpYXNfYXNzZXNzbWVudF90eXBlKQ0KDQojIENyZWF0ZSB0aGUgQWxsdXZpYWwgcGxvdA0KZmlnczE2IDwtIGJpYXNfYXNzZXNzbWVudF9hbGx1dmlhbCAlPiUgDQpnZ3Bsb3QoYWVzKHkgPSBmcmVxICxheGlzMSA9IEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBheGlzMiA9IGJpYXNfYXNzZXNzbWVudF90eXBlKSkgKw0KICBzY2FsZV94X2Rpc2NyZXRlKGxpbWl0cyA9IGMoIkpvdXJuYWwgQ2l0YXRpb24gUmVwb3J0IENhdGVnb3J5IiwgIkJpYXMgQXNzZXNzbWVudCBUeXBlIiksIGV4cGFuZCA9IGMoLjA1LCAuMDUpKSArDQogIHhsYWIoIlZhcmlhYmxlcyIpICsNCiAgZ2VvbV9hbGx1dml1bShhZXMoZmlsbCA9IEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkKSkgKw0KICBnZW9tX3N0cmF0dW0od2lkdGggPSAxLzQsIGZpbGwgPSAid2hpdGUiLCBjb2xvciA9ICJibGFjayIpICsNCiAgZ2VvbV90ZXh0KHN0YXQgPSAic3RyYXR1bSIsIGFlcyhsYWJlbCA9IGFmdGVyX3N0YXQoc3RyYXR1bSkpLCBzaXplID0gNikgKw0KICBsYWJzKHg9ICJWYXJpYWJsZXMiLCB5ID0gIkZyZXF1ZW5jeSIsIGZpbGwgPSAiSm91cm5hbCBDYXRlZ29yeSBBbGxvY2F0ZWQiKSArDQogIHRoZW1lX3N1cHBsKCkNCg0KZmlnczE2DQoNCiBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMTYucGRmIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MxNi5qcGciKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQpgYGANCg0KIyMgRmlndXJlIHMxNyANCkEgYmFyIHBsb3Qgc2hvd2luZyB0aGUgcGVyY2VudGFnZSBhbmQgdG90YWwgY291bnQgb2YgYmlhcyBtZXRob2RvbG9neSB1c2VkIGluIG1ldGEtYW5hbHlzaXMgaW52ZXN0aWdhdGluZyB0aGUgaW1wYWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiBOb3RlOiBzb21lIG1ldGEtYW5hbHlzaXMgbWF5IGNvbnRyaWJ1dGUgdG8gbXVsdGlwbGUgc2VjdGlvbnMgaWYgdGhlIHN0dWR5IGludm9sdmVzIG11bHRpcGxlIGJpYXMgbWV0aG9kb2xvZ2llcyBhcmUgdXNlZCANCmBgYHtyLCBmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIENhbGN1bGF0ZSB0aGUgdG90YWwgY291bnQgZm9yIGVhY2ggY2F0ZWdvcnkNCmJpYXNfbWV0aG9kX2NvdW50IDwtIHNkICU+JSANCiAgc2VwYXJhdGVfcm93cyhiaWFzX2Fzc2Vzc21lbnRfbWV0aG9kLCBzZXAgPSAiLFxccysiKSAlPiUgDQogIGNvdW50KGJpYXNfYXNzZXNzbWVudF9tZXRob2QpICU+JQ0KICBmaWx0ZXIoYmlhc19hc3Nlc3NtZW50X21ldGhvZCAhPSAiTkEiKSAlPiUNCiAgICBncm91cF9ieShiaWFzX2Fzc2Vzc21lbnRfbWV0aG9kKSAlPiUNCiAgc3VtbWFyaXNlKG4gPSBzdW0obikpDQoNCiMgQ2FsY3VsYXRlIHByb3BvcnRpb24gYW5kIHBlcmNlbnRhZ2UgZm9yIGVhY2ggY2F0ZWdvcnkNCmJpYXNfbWV0aG9kX3BjdCA8LSBiaWFzX21ldGhvZF9jb3VudCAlPiUNCiAgbXV0YXRlKHByb3BvcnRpb24gPSBuIC8gc3VtKGJpYXNfbWV0aG9kX2NvdW50JG4pLA0KICAgICAgICAgcGVyY2VudGFnZSA9IHByb3BvcnRpb24gKiAxMDApDQoNCiMgQ3JlYXRlIHRoZSBjb3VudCBwbG90DQpmaWdzMTcgPC0gYmlhc19tZXRob2RfY291bnQgJT4lDQogIGdncGxvdChhZXMoeCA9IG4sIHkgPSByZW9yZGVyKGJpYXNfYXNzZXNzbWVudF9tZXRob2QsIG4pLCBmaWxsID0gIiMxYjllNzciKSkgKw0KICBnZW9tX2JhcihzdGF0ID0gImlkZW50aXR5Iiwgd2lkdGggPSAwLjggLCBhbHBoYSA9IDAuNykgKw0KICBnZW9tX3RleHQoYWVzKGxhYmVsID0gbiwgeCA9IG4gLyAyLCB5ID0gcmVvcmRlcihiaWFzX2Fzc2Vzc21lbnRfbWV0aG9kLCBuKSksIGhqdXN0ID0gMC41LCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChkYXRhID0gYmlhc19tZXRob2RfcGN0LCBhZXMobGFiZWwgPSBwYXN0ZTAoIigiLCByb3VuZChwZXJjZW50YWdlLCAxKSwgIiUpIiksIHggPSBuKSwgDQogICAgICAgICAgICBoanVzdCA9IC0wLjEsIHNpemUgPSA2LCBjb2xvciA9ICJibGFjayIsIGZvbnRmYWNlID0gImJvbGQiKSArDQogIHNjYWxlX2ZpbGxfaWRlbnRpdHkoZ3VpZGUgPSAibm9uZSIpICsNCiAgc2NhbGVfeF9jb250aW51b3VzKG5hbWUgPSAiQXJ0aWNsZSBDb3VudCIsIGV4cGFuZCA9IGMoMCwgMCksIGxpbWl0cyA9IGMoMCwgbWF4KGJpYXNfbWV0aG9kX2NvdW50JG4pKjEuMSkpICsNCiAgbGFicyh5ID0gTlVMTCkgKw0KICB0aGVtZV9zdXBwbCgpDQoNCmZpZ3MxNw0KDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczE3LnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMTcuanBnIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KYGBgDQoNCg0KIyMgRmlndXJlIHMxOA0KQW4gYWxsdXZpYWwgcGxvdCBzaG93aW5nIHRoZSByZWxhdGlvbnNoaXAgYmV0d2VlbiB0aGUgSm91cm5hbCBDaXRhdGlvbiBSZXBvcnQgQ2F0ZWdvcnkgYW5kIGJpYXMgYXNzZXNzbWVudCBtZXRob2QNCmBgYHtyLCBmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIERhdGEgVHJhbnNmb3JtYXRpb24gDQpiaWFzX2Fzc2Vzc21lbnRfYWxsdXZpYWwgPC0gc2QgJT4lIA0KICAgIHNlcGFyYXRlX3Jvd3MoYmlhc19hc3Nlc3NtZW50X21ldGhvZCwgc2VwID0gIixcXHMrIikgJT4lDQogICAgc2VwYXJhdGVfcm93cyhKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgc2VwID0gIi9cXHMrIikgJT4lIA0KICAgIGZpbHRlcighaXMubmEoYmlhc19hc3Nlc3NtZW50X21ldGhvZCkpICU+JQ0KICAgIGdyb3VwX2J5KEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBiaWFzX2Fzc2Vzc21lbnRfbWV0aG9kKSAlPiUgDQogICAgY291bnQoYmlhc19hc3Nlc3NtZW50X21ldGhvZCwgSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpICU+JSANCiAgICBzdW1tYXJpc2UoZnJlcSA9IG4oKSwgLmdyb3VwcyA9ICdkcm9wJykgJT4lIA0KICAgIGdyb3VwX2J5KGJpYXNfYXNzZXNzbWVudF9tZXRob2QpDQoNCiMgQ3JlYXRlIHRoZSBBbGx1dmlhbCBwbG90DQpmaWdzMTggPC0gYmlhc19hc3Nlc3NtZW50X2FsbHV2aWFsICU+JSANCiAgZ2dwbG90KGFlcyh5ID0gZnJlcSAsYXhpczEgPSBKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgYXhpczIgPSBiaWFzX2Fzc2Vzc21lbnRfbWV0aG9kKSkgKw0KICBzY2FsZV94X2Rpc2NyZXRlKGxpbWl0cyA9IGMoIkpvdXJuYWwgQ2l0YXRpb24gUmVwb3J0IENhdGVnb3J5IiwgIkJpYXMgQXNzZXNzbWVudCBNZXRob2QiKSwgZXhwYW5kID0gYyguMDUsIC4wNSkpICsNCiAgeGxhYigiVmFyaWFibGVzIikgKw0KICBnZW9tX2FsbHV2aXVtKGFlcyhmaWxsID0gSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpKSArDQogIGdlb21fc3RyYXR1bSh3aWR0aCA9IDEvNCwgZmlsbCA9ICJ3aGl0ZSIsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoc3RhdCA9ICJzdHJhdHVtIiwgYWVzKGxhYmVsID0gYWZ0ZXJfc3RhdChzdHJhdHVtKSksIHNpemUgPSA2KSArDQogIGxhYnMoeD0gIlZhcmlhYmxlcyIsIHkgPSAiRnJlcXVlbmN5IiwgZmlsbCA9ICJKb3VybmFsIENhdGVnb3J5IEFsbG9jYXRlZCIpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzMTgNCg0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MxOC5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczE4LmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KYGBgDQoNCiMjIEZpZ3VyZSBzMTkNCkEgYmFyIHBsb3Qgc2hvd2luZyB0aGUgcGVyY2VudGFnZSBhbmQgdG90YWwgY291bnQgb2YgYmlhcyB2aXN1YWxpemF0aW9ucyB1c2VkIGluIG1ldGEtYW5hbHlzaXMgaW52ZXN0aWdhdGluZyB0aGUgaW1wYWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiBOb3RlOiBzb21lIG1ldGEtYW5hbHlzaXMgbWF5IGNvbnRyaWJ1dGUgdG8gbXVsdGlwbGUgc2VjdGlvbnMgaWYgdGhlIHN0dWR5IGludm9sdmVzIG11bHRpcGxlIGJpYXMgdmlzdWFsaXphdGlvbnMgYXJlIHVzZWQgDQpgYGB7ciwgZmlnLndpZHRoPTE2LCBmaWcuaGVpZ2h0PTEwfQ0KIyBDYWxjdWxhdGUgdGhlIHRvdGFsIGNvdW50IGZvciBlYWNoIGNhdGVnb3J5DQpiaWFzX3Zpc3VhbGl6YXRpb25fY291bnQgPC0gc2QgJT4lIA0KICBzZXBhcmF0ZV9yb3dzKGJpYXNfYXNzZXNzbWVudF92aXN1YWxpemF0aW9uLCBzZXAgPSAiLFxccysiKSAlPiUgDQogIGNvdW50KGJpYXNfYXNzZXNzbWVudF92aXN1YWxpemF0aW9uKSAlPiUNCiAgZmlsdGVyKGJpYXNfYXNzZXNzbWVudF92aXN1YWxpemF0aW9uICE9ICJOQSIpICU+JQ0KICAgIGdyb3VwX2J5KGJpYXNfYXNzZXNzbWVudF92aXN1YWxpemF0aW9uKSAlPiUNCiAgc3VtbWFyaXNlKG4gPSBzdW0obikpDQoNCiMgQ2FsY3VsYXRlIHByb3BvcnRpb24gYW5kIHBlcmNlbnRhZ2UgZm9yIGVhY2ggY2F0ZWdvcnkNCmJpYXNfdmlzdWFsaXphdGlvbl9wY3QgPC0gYmlhc192aXN1YWxpemF0aW9uX2NvdW50ICU+JQ0KICBtdXRhdGUocHJvcG9ydGlvbiA9IG4gLyBzdW0oYmlhc192aXN1YWxpemF0aW9uX2NvdW50JG4pLA0KICAgICAgICAgcGVyY2VudGFnZSA9IHByb3BvcnRpb24gKiAxMDApDQoNCiMgQ3JlYXRlIHRoZSBjb3VudCBwbG90DQpmaWdzMTkgPC0gYmlhc192aXN1YWxpemF0aW9uX2NvdW50ICU+JQ0KICBnZ3Bsb3QoYWVzKHggPSBuLCB5ID0gcmVvcmRlcihiaWFzX2Fzc2Vzc21lbnRfdmlzdWFsaXphdGlvbiwgbiksIGZpbGwgPSAiIzFiOWU3NyIpKSArDQogIGdlb21fYmFyKHN0YXQgPSAiaWRlbnRpdHkiLCB3aWR0aCA9IDAuOCAsIGFscGhhID0gMC43KSArDQogIGdlb21fdGV4dChhZXMobGFiZWwgPSBuLCB4ID0gbiAvIDIsIHkgPSByZW9yZGVyKGJpYXNfYXNzZXNzbWVudF92aXN1YWxpemF0aW9uLCBuKSksIGhqdXN0ID0gMC41LCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChkYXRhID0gYmlhc192aXN1YWxpemF0aW9uX3BjdCwgYWVzKGxhYmVsID0gcGFzdGUwKCIoIiwgcm91bmQocGVyY2VudGFnZSwgMSksICIlKSIpLCB4ID0gbiksIA0KICAgICAgICAgICAgaGp1c3QgPSAtMC4xLCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siLCBmb250ZmFjZSA9ICJib2xkIikgKw0KICBzY2FsZV9maWxsX2lkZW50aXR5KGd1aWRlID0gIm5vbmUiKSArDQogIHNjYWxlX3hfY29udGludW91cyhuYW1lID0gIkFydGljbGUgQ291bnQiLCBleHBhbmQgPSBjKDAsIDApLCBsaW1pdHMgPSBjKDAsIG1heChiaWFzX3Zpc3VhbGl6YXRpb25fY291bnQkbikqMS4xKSkgKw0KICBsYWJzKHkgPSBOVUxMKSArDQogdGhlbWVfc3VwcGwoKQ0KDQpmaWdzMTkNCg0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MxOS5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczE5LmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCmBgYA0KDQojIyBGaWd1cmUgczIwDQpBbiBhbGx1dmlhbCBwbG90IHNob3dpbmcgdGhlIHJlbGF0aW9uc2hpcCBiZXR3ZWVuIHRoZSBKb3VybmFsIENpdGF0aW9uIFJlcG9ydCBDYXRlZ29yeSBhbmQgYmlhcyB2aXN1YWxpemF0aW9uIG1ldGhvZA0KYGBge3IsIGZpZy53aWR0aD0xNiwgZmlnLmhlaWdodD0xMH0NCiMgRGF0YSBUcmFuc2Zvcm1hdGlvbiANCmJpYXNfdml6dWFsaXNhdGlvbl9hbGx1dmlhbCA8LSBzZCAlPiUgDQogICAgc2VwYXJhdGVfcm93cyhiaWFzX2Fzc2Vzc21lbnRfdmlzdWFsaXphdGlvbiwgc2VwID0gIixcXHMrIikgJT4lDQogICAgc2VwYXJhdGVfcm93cyhKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgc2VwID0gIi9cXHMrIikgJT4lIA0KICAgIGZpbHRlcighaXMubmEoYmlhc19hc3Nlc3NtZW50X3Zpc3VhbGl6YXRpb24pKSAlPiUNCiAgICBncm91cF9ieShKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgYmlhc19hc3Nlc3NtZW50X3Zpc3VhbGl6YXRpb24pICU+JSANCiAgICBjb3VudChiaWFzX2Fzc2Vzc21lbnRfdmlzdWFsaXphdGlvbiwgSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpICU+JSANCiAgICBzdW1tYXJpc2UoZnJlcSA9IG4oKSwgLmdyb3VwcyA9ICdkcm9wJykgJT4lIA0KICAgIGdyb3VwX2J5KGJpYXNfYXNzZXNzbWVudF92aXN1YWxpemF0aW9uKQ0KDQojIENyZWF0ZSB0aGUgQWxsdXZpYWwgcGxvdA0KZmlnczIwIDwtIGJpYXNfdml6dWFsaXNhdGlvbl9hbGx1dmlhbCAlPiUgDQogIGdncGxvdChhZXMoeSA9IGZyZXEgLGF4aXMxID0gSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQsIGF4aXMyID0gYmlhc19hc3Nlc3NtZW50X3Zpc3VhbGl6YXRpb24pKSArDQogIHNjYWxlX3hfZGlzY3JldGUobGltaXRzID0gYygiSm91cm5hbCBDaXRhdGlvbiBSZXBvcnQgQ2F0ZWdvcnkiLCAiQmlhcyBBc3Nlc3NtZW50IE1ldGhvZCIpLCBleHBhbmQgPSBjKC4wNSwgLjA1KSkgKw0KICB4bGFiKCJWYXJpYWJsZXMiKSArDQogIGdlb21fYWxsdXZpdW0oYWVzKGZpbGwgPSBKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCkpICsNCiAgZ2VvbV9zdHJhdHVtKHdpZHRoID0gMS80LCBmaWxsID0gIndoaXRlIiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChzdGF0ID0gInN0cmF0dW0iLCBhZXMobGFiZWwgPSBhZnRlcl9zdGF0KHN0cmF0dW0pKSwgc2l6ZSA9IDYpICsNCiAgbGFicyh4PSAiVmFyaWFibGVzIiwgeSA9ICJGcmVxdWVuY3kiLCBmaWxsID0gIkpvdXJuYWwgQ2F0ZWdvcnkgQWxsb2NhdGVkIikgKw0KICB0aGVtZV9zdXBwbCgpDQoNCmZpZ3MyMA0KDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczIwLnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMjAuanBnIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KDQpgYGANCg0KIyMgRmlndXJlIHMyMSANCkEgYmFyIHBsb3Qgc2hvd2luZyB0aGUgcGVyY2VudGFnZSBhbmQgdG90YWwgY291bnQgb2YgcmlzayBvZiBiaWFzIHRlc3RzIHVzZWQgaW4gbWV0YS1hbmFseXNpcyBpbnZlc3RpZ2F0aW5nIHRoZSBpbXBhY3RzIG9mIG9yZ2Fub2NobG9yaW5lIHBlc3RpY2lkZXMuIE5vdGU6IHNvbWUgbWV0YS1hbmFseXNpcyBtYXkgY29udHJpYnV0ZSB0byBtdWx0aXBsZSBzZWN0aW9ucyBpZiB0aGUgc3R1ZHkgaW52b2x2ZXMgbXVsdGlwbGUgcmlzayBvZiBiaWFzIHRlc3RzIGFyZSB1c2VkIA0KYGBge3IsIGZpZy53aWR0aD0xNiwgZmlnLmhlaWdodD0xMH0NCiMgQ2FsY3VsYXRlIHRoZSB0b3RhbCBjb3VudCBmb3IgZWFjaCBjYXRlZ29yeQ0Kcm9iX21ldGhvZF9jb3VudCA8LSBzZCAlPiUgDQogIHNlcGFyYXRlX3Jvd3Mocm9iX2Fzc2Vzc21lbnRfbWV0aG9kLCBzZXAgPSAiLFxccysiKSAlPiUgDQogIGNvdW50KHJvYl9hc3Nlc3NtZW50X21ldGhvZCkgJT4lDQogIGZpbHRlcihyb2JfYXNzZXNzbWVudF9tZXRob2QgIT0gIk5BIikgJT4lDQogIGdyb3VwX2J5KHJvYl9hc3Nlc3NtZW50X21ldGhvZCkgJT4lDQogIHN1bW1hcmlzZShuID0gc3VtKG4pKQ0KDQojIENhbGN1bGF0ZSBwcm9wb3J0aW9uIGFuZCBwZXJjZW50YWdlIGZvciBlYWNoIGNhdGVnb3J5DQpyb2JfbWV0aG9kX3BjdCA8LSByb2JfbWV0aG9kX2NvdW50ICU+JQ0KICBtdXRhdGUocHJvcG9ydGlvbiA9IG4gLyBzdW0ocm9iX21ldGhvZF9jb3VudCRuKSwNCiAgICAgICAgIHBlcmNlbnRhZ2UgPSBwcm9wb3J0aW9uICogMTAwKQ0KDQojIENyZWF0ZSB0aGUgY291bnQgcGxvdA0KZmlnczIxIDwtIHJvYl9tZXRob2RfY291bnQgJT4lDQogIGdncGxvdChhZXMoeCA9IG4sIHkgPSByZW9yZGVyKHJvYl9hc3Nlc3NtZW50X21ldGhvZCwgbiksIGZpbGwgPSAiIzFiOWU3NyIpKSArDQogIGdlb21fYmFyKHN0YXQgPSAiaWRlbnRpdHkiLCB3aWR0aCA9IDAuOCAsIGFscGhhID0gMC43KSArDQogIGdlb21fdGV4dChhZXMobGFiZWwgPSBuLCB4ID0gbiAvIDIsIHkgPSByZW9yZGVyKHJvYl9hc3Nlc3NtZW50X21ldGhvZCwgbikpLCBoanVzdCA9IDAuNSwgc2l6ZSA9IDYsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoZGF0YSA9IHJvYl9tZXRob2RfcGN0LCBhZXMobGFiZWwgPSBwYXN0ZTAoIigiLCByb3VuZChwZXJjZW50YWdlLCAwKSwgIiUpIiksIHggPSBuKSwgDQogICAgICAgICAgICBoanVzdCA9IC0wLjEsIHNpemUgPSA2LCBjb2xvciA9ICJibGFjayIsIGZvbnRmYWNlID0gImJvbGQiKSArDQogIHNjYWxlX2ZpbGxfaWRlbnRpdHkoZ3VpZGUgPSAibm9uZSIpICsNCiAgc2NhbGVfeF9jb250aW51b3VzKG5hbWUgPSAiQXJ0aWNsZSBDb3VudCIsIGV4cGFuZCA9IGMoMCwgMCksIGxpbWl0cyA9IGMoMCwgbWF4KHJvYl9tZXRob2RfY291bnQkbikqMS4xKSkgKw0KICBsYWJzKHkgPSBOVUxMKSArDQogIHRoZW1lX3N1cHBsKCkNCg0KZmlnczIxDQoNCiBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMjEucGRmIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MyMS5qcGciKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQpgYGANCg0KIyMgRmlndXJlIHMyMg0KQW4gYWxsdXZpYWwgcGxvdCBzaG93aW5nIHRoZSByZWxhdGlvbnNoaXAgYmV0d2VlbiB0aGUgSm91cm5hbCBDaXRhdGlvbiBSZXBvcnQgQ2F0ZWdvcnkgYW5kIHJpc2sgb2YgYmlhcyBtZXRob2RvbG9neSANCmBgYHtyLCBmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIERhdGEgVHJhbnNmb3JtYXRpb24gDQpyb2JtZXRob2RfYWxsdXZpYWwgPC0gc2QgJT4lIA0KICAgICBzZXBhcmF0ZV9yb3dzKHJvYl9hc3Nlc3NtZW50X21ldGhvZCwgc2VwID0gIixcXHMrIikgJT4lDQogICAgZmlsdGVyKCFpcy5uYShyb2JfYXNzZXNzbWVudF9tZXRob2QpKSAlPiUNCiAgICBzZXBhcmF0ZV9yb3dzKEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBzZXAgPSAiL1xccysiKSAlPiUNCiAgICBncm91cF9ieShKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgcm9iX2Fzc2Vzc21lbnRfbWV0aG9kKSAlPiUgDQogICAgY291bnQocm9iX2Fzc2Vzc21lbnRfbWV0aG9kLCBKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCkgJT4lIA0KICAgIHN1bW1hcmlzZShmcmVxID0gbigpLCAuZ3JvdXBzID0gJ2Ryb3AnKSAlPiUgDQogICAgZ3JvdXBfYnkocm9iX2Fzc2Vzc21lbnRfbWV0aG9kKSANCg0KDQojIENyZWF0ZSB0aGUgQWxsdXZpYWwgcGxvdA0KZmlnczIyIDwtIHJvYm1ldGhvZF9hbGx1dmlhbCAlPiUgDQpnZ3Bsb3QoYWVzKHkgPSBmcmVxICxheGlzMSA9IEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBheGlzMiA9IHJvYl9hc3Nlc3NtZW50X21ldGhvZCkpICsNCiAgc2NhbGVfeF9kaXNjcmV0ZShsaW1pdHMgPSBjKCJKb3VybmFsIENpdGF0aW9uIFJlcG9ydCBDYXRlZ29yeSIsICJST0IgQXNzZXNzbWVudCBNZXRob2QiKSwgZXhwYW5kID0gYyguMDUsIC4wNSkpICsNCiAgeGxhYigiVmFyaWFibGVzIikgKw0KICBnZW9tX2FsbHV2aXVtKGFlcyhmaWxsID0gSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpKSArDQogIGdlb21fc3RyYXR1bSh3aWR0aCA9IDEvNCwgZmlsbCA9ICJ3aGl0ZSIsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoc3RhdCA9ICJzdHJhdHVtIiwgYWVzKGxhYmVsID0gYWZ0ZXJfc3RhdChzdHJhdHVtKSksIHNpemUgPSA2KSArDQogIGxhYnMoeD0gIlZhcmlhYmxlcyIsIHkgPSAiRnJlcXVlbmN5IiwgZmlsbCA9ICJKb3VybmFsIENhdGVnb3J5IEFsbG9jYXRlZCIpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzMjINCg0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MyMi5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczIyLmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KYGBgDQoNCiMjIEZpZ3VyZSBzMjMNCkEgYmFyIHBsb3Qgc2hvd2luZyB0aGUgcGVyY2VudGFnZSBhbmQgdG90YWwgY291bnQgb2YgdmlzdWFsaXphdGlvbiBtZXRob2RzIHVzZWQgaW4gbWV0YS1hbmFseXNpcyBpbnZlc3RpZ2F0aW5nIHRoZSBpbXBhY3RzIG9mIG9yZ2Fub2NobG9yaW5lIHBlc3RpY2lkZXMuIE5vdGU6IHNvbWUgbWV0YS1hbmFseXNpcyBtYXkgY29udHJpYnV0ZSB0byBtdWx0aXBsZSBzZWN0aW9ucyBpZiB0aGUgc3R1ZHkgaW52b2x2ZXMgbXVsdGlwbGUgdmlzdWFsaXphdGlvbiBtZXRob2RzIGFyZSB1c2VkDQpgYGB7ciwgZmlnLndpZHRoPTE2LCBmaWcuaGVpZ2h0PTEwfQ0KIyBDYWxjdWxhdGUgdGhlIHRvdGFsIGNvdW50IGZvciBlYWNoIGNhdGVnb3J5DQp2aXN1YWxpemF0aW9uX2NvdW50IDwtIHNkICU+JSANCiAgc2VwYXJhdGVfcm93cyh2aXN1YWxpemF0aW9uX21ldGhvZCwgc2VwID0gIixcXHMrIikgJT4lIA0KICBjb3VudCh2aXN1YWxpemF0aW9uX21ldGhvZCkgJT4lDQogIGZpbHRlcih2aXN1YWxpemF0aW9uX21ldGhvZCAhPSAiTkEiKSAlPiUNCiAgICBncm91cF9ieSh2aXN1YWxpemF0aW9uX21ldGhvZCkgJT4lDQogIHN1bW1hcmlzZShuID0gc3VtKG4pKQ0KDQojIENhbGN1bGF0ZSBwcm9wb3J0aW9uIGFuZCBwZXJjZW50YWdlIGZvciBlYWNoIGNhdGVnb3J5DQp2aXN1YWxpemF0aW9uX3BjdCA8LSB2aXN1YWxpemF0aW9uX2NvdW50ICU+JQ0KICBtdXRhdGUocHJvcG9ydGlvbiA9IG4gLyBzdW0odmlzdWFsaXphdGlvbl9jb3VudCRuKSwNCiAgICAgICAgIHBlcmNlbnRhZ2UgPSBwcm9wb3J0aW9uICogMTAwKQ0KDQojIENyZWF0ZSB0aGUgY291bnQgcGxvdA0KZmlnczIzIDwtIHZpc3VhbGl6YXRpb25fY291bnQgJT4lDQogIGdncGxvdChhZXMoeCA9IG4sIHkgPSByZW9yZGVyKHZpc3VhbGl6YXRpb25fbWV0aG9kLCBuKSwgZmlsbCA9ICIjMWI5ZTc3IikpICsNCiAgZ2VvbV9iYXIoc3RhdCA9ICJpZGVudGl0eSIsIHdpZHRoID0gMC44ICwgYWxwaGEgPSAwLjcpICsNCiAgZ2VvbV90ZXh0KGFlcyhsYWJlbCA9IG4sIHggPSBuIC8gMiwgeSA9IHJlb3JkZXIodmlzdWFsaXphdGlvbl9tZXRob2QsIG4pKSwgaGp1c3QgPSAwLjUsIHNpemUgPSA2LCBjb2xvciA9ICJibGFjayIpICsNCiAgZ2VvbV90ZXh0KGRhdGEgPSB2aXN1YWxpemF0aW9uX3BjdCwgYWVzKGxhYmVsID0gcGFzdGUwKCIoIiwgcm91bmQocGVyY2VudGFnZSwgMCksICIlKSIpLCB4ID0gbiksIA0KICAgICAgICAgICAgaGp1c3QgPSAtMC4xLCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siLCBmb250ZmFjZSA9ICJib2xkIikgKw0KICBzY2FsZV9maWxsX2lkZW50aXR5KGd1aWRlID0gIm5vbmUiKSArDQogIHNjYWxlX3hfY29udGludW91cyhuYW1lID0gIkFydGljbGUgQ291bnQiLCBleHBhbmQgPSBjKDAsIDApLCBsaW1pdHMgPSBjKDAsIG1heCh2aXN1YWxpemF0aW9uX2NvdW50JG4pKjEuMSkpICsNCiAgbGFicyh5ID0gTlVMTCkgKw0KICB0aGVtZV9zdXBwbCgpDQoNCmZpZ3MyMw0KDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczIzLnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMjMuanBnIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KYGBgDQoNCiMjIEZpZ3VyZSBzMjQNCkFuIGFsbHV2aWFsIHBsb3Qgc2hvd2luZyB0aGUgcmVsYXRpb25zaGlwIGJldHdlZW4gdGhlIEpvdXJuYWwgQ2l0YXRpb24gUmVwb3J0IENhdGVnb3J5IGFuZCB2aXN1YWxpemF0aW9uIG1ldGhvZCANCmBgYHtyLCBmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIERhdGEgVHJhbnNmb3JtYXRpb24gDQp2aXp1YWxpemF0aW9uX2FsbHV2aWFsIDwtIHNkICU+JSANCiAgICBzZXBhcmF0ZV9yb3dzKHZpc3VhbGl6YXRpb25fbWV0aG9kLCBzZXAgPSAiLFxccysiKSAlPiUNCiAgICBmaWx0ZXIoIWlzLm5hKHZpc3VhbGl6YXRpb25fbWV0aG9kKSkgJT4lDQogICAgc2VwYXJhdGVfcm93cyhKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCwgc2VwID0gIi9cXHMrIikgJT4lDQogICAgZ3JvdXBfYnkoSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQsIHZpc3VhbGl6YXRpb25fbWV0aG9kKSAlPiUgDQogICAgY291bnQodmlzdWFsaXphdGlvbl9tZXRob2QsIEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkKSAlPiUgDQogICAgc3VtbWFyaXNlKGZyZXEgPSBuKCksIC5ncm91cHMgPSAnZHJvcCcpICU+JSANCiAgICBncm91cF9ieSh2aXN1YWxpemF0aW9uX21ldGhvZCkgDQoNCg0KIyBDcmVhdGUgdGhlIEFsbHV2aWFsIHBsb3QNCmZpZ3MyNCA8LSB2aXp1YWxpemF0aW9uX2FsbHV2aWFsICU+JSANCmdncGxvdChhZXMoeSA9IGZyZXEgLGF4aXMxID0gSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQsIGF4aXMyID0gdmlzdWFsaXphdGlvbl9tZXRob2QpKSArDQogIHNjYWxlX3hfZGlzY3JldGUobGltaXRzID0gYygiSm91cm5hbCBDaXRhdGlvbiBSZXBvcnQgQ2F0ZWdvcnkiLCAiUk9CIEFzc2Vzc21lbnQgTWV0aG9kIiksIGV4cGFuZCA9IGMoLjA1LCAuMDUpKSArDQogIHhsYWIoIlZhcmlhYmxlcyIpICsNCiAgZ2VvbV9hbGx1dml1bShhZXMoZmlsbCA9IEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkKSkgKw0KICBnZW9tX3N0cmF0dW0od2lkdGggPSAxLzQsIGZpbGwgPSAid2hpdGUiLCBjb2xvciA9ICJibGFjayIpICsNCiAgZ2VvbV90ZXh0KHN0YXQgPSAic3RyYXR1bSIsIGFlcyhsYWJlbCA9IGFmdGVyX3N0YXQoc3RyYXR1bSkpLCBzaXplID0gNikgKw0KICBsYWJzKHg9ICJWYXJpYWJsZXMiLCB5ID0gIkZyZXF1ZW5jeSIsIGZpbGwgPSAiSm91cm5hbCBDYXRlZ29yeSBBbGxvY2F0ZWQiKSArDQogIHRoZW1lX3N1cHBsKCkNCg0KZmlnczI0DQoNCiAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczI0LnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczI0LmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KYGBgDQoNCiMjIEZpZ3VyZSBzMjUNCkEgYmFyIHBsb3Qgc2hvd2luZyB0aGUgcGVyY2VudGFnZSBhbmQgdG90YWwgY291bnQgb2YgcmVwb3J0aW5nIGd1aWRlbGluZXMgdXNlZCBpbiBtZXRhLWFuYWx5c2lzIGludmVzdGlnYXRpbmcgdGhlIGltcGFjdHMgb2Ygb3JnYW5vY2hsb3JpbmUgcGVzdGljaWRlcy4gTm90ZTogc29tZSBtZXRhLWFuYWx5c2lzIG1heSBjb250cmlidXRlIHRvIG11bHRpcGxlIHNlY3Rpb25zIGlmIHRoZSBzdHVkeSBpbnZvbHZlcyBtdWx0aXBsZSByZXBvcnRpbmcgZ3VpZGVsaW5lcyBhcmUgdXNlZA0KYGBge3IsIGZpZy53aWR0aD0xNiwgZmlnLmhlaWdodD0xMH0NCiMgQ2FsY3VsYXRlIHRoZSB0b3RhbCBjb3VudCBmb3IgZWFjaCBjYXRlZ29yeQ0KcmVwb3J0aW5nX2d1aWRlX2NvdW50IDwtIHNkICU+JSANCiAgc2VwYXJhdGVfcm93cyhyZXBvcnRpbmdfc3RhbmRhcmRzX3R5cGUsIHNlcCA9ICIsXFxzKyIpICU+JSANCiAgY291bnQocmVwb3J0aW5nX3N0YW5kYXJkc190eXBlKSAlPiUNCiAgZmlsdGVyKHJlcG9ydGluZ19zdGFuZGFyZHNfdHlwZSAhPSAiTkEiKSAlPiUNCiAgICBncm91cF9ieShyZXBvcnRpbmdfc3RhbmRhcmRzX3R5cGUpICU+JQ0KICBzdW1tYXJpc2UobiA9IHN1bShuKSkNCg0KIyBDYWxjdWxhdGUgcHJvcG9ydGlvbiBhbmQgcGVyY2VudGFnZSBmb3IgZWFjaCBjYXRlZ29yeQ0KcmVwb3J0aW5nX2d1aWRlX3BjdCA8LSByZXBvcnRpbmdfZ3VpZGVfY291bnQgJT4lDQogIG11dGF0ZShwcm9wb3J0aW9uID0gbiAvIHN1bShyZXBvcnRpbmdfZ3VpZGVfY291bnQkbiksDQogICAgICAgICBwZXJjZW50YWdlID0gcHJvcG9ydGlvbiAqIDEwMCkNCg0KIyBDcmVhdGUgdGhlIGNvdW50IHBsb3QNCmZpZ3MyNSA8LSByZXBvcnRpbmdfZ3VpZGVfY291bnQgJT4lDQogIGdncGxvdChhZXMoeCA9IG4sIHkgPSByZW9yZGVyKHJlcG9ydGluZ19zdGFuZGFyZHNfdHlwZSwgbiksIGZpbGwgPSAiIzFiOWU3NyIpKSArDQogIGdlb21fYmFyKHN0YXQgPSAiaWRlbnRpdHkiLCB3aWR0aCA9IDAuOCAsIGFscGhhID0gMC43KSArDQogIGdlb21fdGV4dChhZXMobGFiZWwgPSBuLCB4ID0gbiAvIDIsIHkgPSByZW9yZGVyKHJlcG9ydGluZ19zdGFuZGFyZHNfdHlwZSwgbikpLCBoanVzdCA9IDAuNSwgc2l6ZSA9IDYsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoZGF0YSA9IHJlcG9ydGluZ19ndWlkZV9wY3QsIGFlcyhsYWJlbCA9IHBhc3RlMCgiKCIsIHJvdW5kKHBlcmNlbnRhZ2UsIDApLCAiJSkiKSwgeCA9IG4pLCANCiAgICAgICAgICAgIGhqdXN0ID0gLTAuMSwgc2l6ZSA9IDYsIGNvbG9yID0gImJsYWNrIiwgZm9udGZhY2UgPSAiYm9sZCIpICsNCiAgc2NhbGVfZmlsbF9pZGVudGl0eShndWlkZSA9ICJub25lIikgKw0KICBzY2FsZV94X2NvbnRpbnVvdXMobmFtZSA9ICJBcnRpY2xlIENvdW50IiwgZXhwYW5kID0gYygwLCAwKSwgbGltaXRzID0gYygwLCBtYXgocmVwb3J0aW5nX2d1aWRlX2NvdW50JG4pKjEuMSkpICsNCiAgbGFicyh5ID0gTlVMTCkgKw0KICB0aGVtZV9zdXBwbCgpDQoNCmZpZ3MyNQ0KDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczI1LnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMjUuanBnIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KYGBgDQoNCiMjIEZpZ3VyZSBzMjYNCkFuIGFsbHV2aWFsIHBsb3Qgc2hvd2luZyB0aGUgcmVsYXRpb25zaGlwIGJldHdlZW4gdGhlIEpvdXJuYWwgQ2l0YXRpb24gUmVwb3J0IENhdGVnb3J5IGFuZCByZXBvcnRpbmcgZ3VpZGVsaW5lIHVzZWQgDQpgYGB7ciwgZmlnLndpZHRoPTE2LCBmaWcuaGVpZ2h0PTEwfQ0KIyBEYXRhIFRyYW5zZm9ybWF0aW9uIA0KcmVwb3J0aW5nX3N0YW5kYXJkc19hbGx1dmlhbCA8LSBzZCAlPiUgDQogICAgc2VwYXJhdGVfcm93cyhyZXBvcnRpbmdfc3RhbmRhcmRzX3R5cGUsIHNlcCA9ICIsXFxzKyIpICU+JQ0KICAgIHNlcGFyYXRlX3Jvd3MoSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQsIHNlcCA9ICIvXFxzKyIpICU+JQ0KICAgIGZpbHRlcighZ3JlcGwoIm5vIGNhdGVnb3J5IGZvdW5kIiwgSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQsIGlnbm9yZS5jYXNlID0gVFJVRSkpICU+JSANCiAgICBmaWx0ZXIoIWlzLm5hKHJlcG9ydGluZ19zdGFuZGFyZHNfdHlwZSkpICU+JQ0KICAgIGdyb3VwX2J5KEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCByZXBvcnRpbmdfc3RhbmRhcmRzX3R5cGUpICU+JSANCiAgICBjb3VudChyZXBvcnRpbmdfc3RhbmRhcmRzX3R5cGUsIEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkKSAlPiUgDQogICAgc3VtbWFyaXNlKGZyZXEgPSBuKCksIC5ncm91cHMgPSAnZHJvcCcpICU+JSANCiAgICBncm91cF9ieShyZXBvcnRpbmdfc3RhbmRhcmRzX3R5cGUpDQoNCg0KIyBDcmVhdGUgdGhlIEFsbHV2aWFsIHBsb3QNCmZpZ3MyNiA8LSByZXBvcnRpbmdfc3RhbmRhcmRzX2FsbHV2aWFsICU+JSANCmdncGxvdCggYWVzKHkgPSBmcmVxICxheGlzMSA9IEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkLCBheGlzMiA9IHJlcG9ydGluZ19zdGFuZGFyZHNfdHlwZSkpICsNCiAgc2NhbGVfeF9kaXNjcmV0ZShsaW1pdHMgPSBjKCJKb3VybmFsIENpdGF0aW9uIFJlcG9ydCBDYXRlZ29yeSIsICJSZXBvcnRpbmcgU3RhbmRhcmRzIFR5cGUiKSwgZXhwYW5kID0gYyguMDUsIC4wNSkpICsNCiAgeGxhYigiVmFyaWFibGVzIikgKw0KICBnZW9tX2FsbHV2aXVtKGFlcyhmaWxsID0gSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQpKSArDQogIGdlb21fc3RyYXR1bSh3aWR0aCA9IDEvNCwgZmlsbCA9ICJ3aGl0ZSIsIGNvbG9yID0gImJsYWNrIikgKw0KICBsYWJzKHg9ICJWYXJpYWJsZXMiLCB5ID0gIkZyZXF1ZW5jeSIsIGZpbGwgPSAiSm91cm5hbCBDYXRlZ29yeSBBbGxvY2F0ZWQiKSArDQogIGdlb21fdGV4dChzdGF0ID0gInN0cmF0dW0iLCBhZXMobGFiZWwgPSBhZnRlcl9zdGF0KHN0cmF0dW0pKSwgc2l6ZSA9IDYpICsNCiAgdGhlbWVfc3VwcGwoKQ0KDQpmaWdzMjYNCg0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MyNi5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczI2LmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCmBgYA0KDQoNCiMjIEZpZ3VyZSAyDQpBIGNpcmN1bGFyIHRyZWVtYXAgc2hvd2luZyB0aGUgY291bnRzIG9mIGVhY2ggbWV0aG9kb2xvZ2ljYWwgaXRlbSBpbiBleGlzaXRuZyBtZXRhLWFuYWx5c2lzIGludmVzdGlnYXRpbmcgdGhlIGltcGFjdHMgb2Ygb3JnYW5vY2hsb3JpbmUgcGVzdGljaWRlcw0KYGBge3IsIGZpZy53aWR0aD0yMSwgZmlnLmhlaWdodD0xNX0NCiMgR3JvdXBpbmcgIk1lZGxpbmUiIGFuZCAiUHVibWVkIiB1bmRlciAiUHViTWVkIiBhbmQgc3VtbWluZyB0aGUgY291bnRzDQpkYXRhYmFzZV9jb3VudCA8LSBkYXRhYmFzZV9jb3VudCAlPiUNCiAgbXV0YXRlKGRhdGFiYXNlX3NlYXJjaCA9IGlmX2Vsc2UoZGF0YWJhc2Vfc2VhcmNoICVpbiUgYygiTWVkbGluZSIsICJQdWJtZWQiKSwgIlB1Yk1lZCIsIGRhdGFiYXNlX3NlYXJjaCkpICU+JQ0KICBncm91cF9ieShkYXRhYmFzZV9zZWFyY2gpICU+JQ0KICBzdW1tYXJpc2UobiA9IHN1bShuKSkNCg0KIyBTcGxpdHRpbmcsIGdyb3VwaW5nLCBhbmQgc3VtbWluZyBkaWZmZXJlbnQgY2F0ZWdvcmllcyBvZiBlZmZlY3Qgc2l6ZXMNCmVmZmVjdHNpemVfY291bnQgPC0gc2QgJT4lIA0KICBzZXBhcmF0ZV9yb3dzKGVmZmVjdF9zaXplLCBzZXAgPSAiLFxccysiKSAlPiUgDQogIGNvdW50KGVmZmVjdF9zaXplKSAlPiUNCiAgZmlsdGVyKGVmZmVjdF9zaXplICE9ICJOQSIpICU+JQ0KICBncm91cF9ieShlZmZlY3Rfc2l6ZSkgJT4lDQogIHN1bW1hcmlzZShuID0gc3VtKG4pKQ0KDQplZmZlY3RzaXplX2NvdW50IDwtIGVmZmVjdHNpemVfY291bnQgJT4lIA0KICBtdXRhdGUoZWZmZWN0X3NpemUgPSBpZl9lbHNlKGVmZmVjdF9zaXplICVpbiUgYygiQmV0YSByZWdyZXNzaW9uIGNvZWZmaWNpZW50IiwgIkNvcnJlbGF0aW9uIGNvZWZmaWNpZW50IiksICJDb3JyZWxhdGlvbiIsIGVmZmVjdF9zaXplKSkgJT4lIA0KICBtdXRhdGUoZWZmZWN0X3NpemUgPSBpZl9lbHNlKGVmZmVjdF9zaXplICVpbiUgYygiT1IgKG9kZHMgcmF0aW8pIiwgIlJSIChyZXNwb25zZSByYXRpbykiLCAiU01EIChzdGFuZGFyZGl6ZWQgbWVhbiBkaWZmZXJlbmNlKSIsICJsblBSIChsb2cgcGFydGl0aW9uaW5nIHJhdGlvKSIsICJsbk9SIChsb2cgb2RkcyByYXRpbykiLCAiUmF0aW8gb2YgbWVhbnMiLCAiSW5SUiAobG9nIHJlc3BvbnNlIHJhdGlvKSIpLCAiTWVhbiBkaWZmZXJlbmNlIiwgZWZmZWN0X3NpemUpKSAlPiUgDQogIG11dGF0ZShlZmZlY3Rfc2l6ZSA9IGlmX2Vsc2UoZWZmZWN0X3NpemUgJWluJSBjKCJsbkNWUiAobG9nIGNvZWZmaWNpZW50IHZhcmlhdGlvbiByYXRpbykiKSwgIlZhcmlhdGlvbiBkaWZmZXJlbmNlIiwgZWZmZWN0X3NpemUpKSAlPiUgDQogIG11dGF0ZShlZmZlY3Rfc2l6ZSA9IGlmX2Vsc2UoZWZmZWN0X3NpemUgJWluJSBjKCJSUiAocmlzayByYXRpbykiKSwgIjJ4MiIsIGVmZmVjdF9zaXplKSkgJT4lIA0KICBtdXRhdGUoZWZmZWN0X3NpemUgPSBpZl9lbHNlKGVmZmVjdF9zaXplICVpbiUgYygiUmF3IHdlaWdodCIsICJUcmFuc2ZlciByYXRlIiwgIkdlb21ldHJpYyBtZWFuIiwgIk1hdGVybmFsIHRyYW5zZmVyIHJhdGlvIiwgIlNNUiAoc3RhbmRhcmRpemVkIG1vcnRhbGl0eSByYXRlKSIsICJUcmFuc2ZlciByYXRlIiwgInotc2NvcmUiKSwgIk90aGVyIEVTIiwgZWZmZWN0X3NpemUpKSAlPiUgDQogIGdyb3VwX2J5KGVmZmVjdF9zaXplKSAlPiUNCiAgc3VtbWFyaXNlKG4gPSBzdW0obikpDQoNCiMgQ2F0ZWdvcml6aW5nIHNvZnR3YXJlIGFzIGVpdGhlciAiQ29kZS1iYXNlZCBzb2Z0d2FyZSIgb3IgIkdVSSIgYW5kIHN1bW1pbmcgdGhlIGNvdW50cw0Kc29mdHdhcmVfY291bnQgPC0gc29mdHdhcmVfY291bnQgJT4lDQogIG11dGF0ZShzb2Z0d2FyZV9hbmFseXNpcyA9IGlmX2Vsc2Uoc29mdHdhcmVfYW5hbHlzaXMgJWluJSBjKCJTdGF0YSIsICJSIiksICJDb2RlLWJhc2VkIHNvZnR3YXJlIiwgc29mdHdhcmVfYW5hbHlzaXMpKSAlPiUNCiAgbXV0YXRlKHNvZnR3YXJlX2FuYWx5c2lzID0gaWZfZWxzZShzb2Z0d2FyZV9hbmFseXNpcyAlaW4lIGMoIkNNQVMiLCAiRXhjZWwiLCAiUmV2TWFuIiwgIlNBUyIsICJYTFNUQVQiKSwgIkdVSSIsIHNvZnR3YXJlX2FuYWx5c2lzKSkgJT4lIA0KICBncm91cF9ieShzb2Z0d2FyZV9hbmFseXNpcykgJT4lDQogIHN1bW1hcmlzZShuID0gc3VtKG4pKQ0KDQojIEdyb3VwaW5nIGhldGVyb2dlbmVpdHkgYXNzZXNzbWVudCBtZXRob2RzIGFuZCBzdW1taW5nIHRoZSBjb3VudHMNCmhldGVyb2dlbmVpdHlfY291bnQgPC0gaGV0ZXJvZ2VuZWl0eV9jb3VudCAlPiUgDQogIG11dGF0ZShoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kID0gaWZfZWxzZShoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kICVpbiUgYygiVGF1IHNxdWFyZSIpLCAiSSBzcXVhcmUiLCBoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kKSkgJT4lIA0KICBtdXRhdGUoaGV0ZXJvZ2VuZWl0eV9hc3Nlc3NtZW50X21ldGhvZCA9IGlmX2Vsc2UoaGV0ZXJvZ2VuZWl0eV9hc3Nlc3NtZW50X21ldGhvZCAlaW4lIGMoIkNoaSBzcXVhcmUiKSwgIlEgc3RhdGlzdGljIiwgaGV0ZXJvZ2VuZWl0eV9hc3Nlc3NtZW50X21ldGhvZCkpICU+JSANCiAgbXV0YXRlKGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QgPSBpZl9lbHNlKGhldGVyb2dlbmVpdHlfYXNzZXNzbWVudF9tZXRob2QgJWluJSBjKCJHYWxicmFpdGggcGxvdCIsICJCYXVqYXRzIHBsb3QiKSwgIlBsb3QiLCBoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kKSkgJT4lIA0KICBncm91cF9ieShoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kKSAlPiUNCiAgc3VtbWFyaXNlKG4gPSBzdW0obikpDQoNCiMgR3JvdXBpbmcgYmlhcyBhc3Nlc3NtZW50IG1ldGhvZHMgd2l0aCBjb3VudCA8PSAzIHVuZGVyICJPdGhlciBCQSIgYW5kIHN1bW1pbmcgdGhlIGNvdW50cw0KYmlhc19tZXRob2RfY291bnQgPC0gYmlhc19tZXRob2RfY291bnQgJT4lIA0KICBtdXRhdGUoYmlhc19hc3Nlc3NtZW50X21ldGhvZCA9IGlmZWxzZShuPD0gMywgIk90aGVyIEJBIiwgYXMuY2hhcmFjdGVyKGJpYXNfYXNzZXNzbWVudF9tZXRob2QpKSkgJT4lIA0KICBncm91cF9ieShiaWFzX2Fzc2Vzc21lbnRfbWV0aG9kKSAlPiUNCiAgc3VtbWFyaXNlKG4gPSBzdW0obikpDQoNCiMgR3JvdXBpbmcgc2Vuc2l0aXZpdHkgYW5hbHlzaXMgbWV0aG9kcyB3aXRoIGNvdW50IDw9IDMgdW5kZXIgIk90aGVyIFNBIiBhbmQgc3VtbWluZyB0aGUgY291bnRzDQpzZW5zaXRpdml0eV9jb3VudCA8LSAgc2Vuc2l0aXZpdHlfY291bnQgJT4lICANCiAgbXV0YXRlKHNlbnNpdGl2aXR5X2FuYWx5c2lzX21ldGhvZCA9IGlmZWxzZShuPD0gMywgIk90aGVyIFNBIiwgYXMuY2hhcmFjdGVyKHNlbnNpdGl2aXR5X2FuYWx5c2lzX21ldGhvZCkpKSAlPiUgDQogIGdyb3VwX2J5KHNlbnNpdGl2aXR5X2FuYWx5c2lzX21ldGhvZCkgJT4lDQogIHN1bW1hcmlzZShuID0gc3VtKG4pKQ0KDQojIEdyb3VwaW5nIHJpc2sgb2YgYmlhcyBhc3Nlc3NtZW50IG1ldGhvZHMgd2l0aCBjb3VudCA8PSAzIHVuZGVyICJPdGhlciBST0IiIGFuZCBzdW1taW5nIHRoZSBjb3VudHMNCnJvYl9tZXRob2RfY291bnQgPC0gIHJvYl9tZXRob2RfY291bnQgJT4lICANCiAgbXV0YXRlKHJvYl9hc3Nlc3NtZW50X21ldGhvZCA9IGlmZWxzZShuPD0gMywgIk90aGVyIFJPQiIsIGFzLmNoYXJhY3Rlcihyb2JfYXNzZXNzbWVudF9tZXRob2QpKSkgJT4lIA0KICBncm91cF9ieShyb2JfYXNzZXNzbWVudF9tZXRob2QpICU+JQ0KICBzdW1tYXJpc2UobiA9IHN1bShuKSkNCg0KIyBHcm91cGluZyB2aXN1YWxpemF0aW9uIG1ldGhvZHMgd2l0aCBjb3VudCA8PSAzIHVuZGVyICJPdGhlciBWaXoiIGFuZCBzdW1taW5nIHRoZSBjb3VudHMNCnZpc3VhbGl6YXRpb25fY291bnQgPC0gdmlzdWFsaXphdGlvbl9jb3VudCAlPiUgDQogIG11dGF0ZSh2aXN1YWxpemF0aW9uX21ldGhvZCA9IGlmZWxzZShuPD0gMywgIk90aGVyIFZpeiIsIGFzLmNoYXJhY3Rlcih2aXN1YWxpemF0aW9uX21ldGhvZCkpKSAlPiUgDQogIGdyb3VwX2J5KHZpc3VhbGl6YXRpb25fbWV0aG9kKSAlPiUNCiAgc3VtbWFyaXNlKG4gPSBzdW0obikpDQoNCiMgR3JvdXBpbmcgcmVwb3J0aW5nIHN0YW5kYXJkcyB0eXBlcyB3aXRoIGNvdW50IDw9IDIgdW5kZXIgIk90aGVyIGd1aWRlbGluZSIgYW5kIHN1bW1pbmcgdGhlIGNvdW50cw0KcmVwb3J0aW5nX2d1aWRlX2NvdW50IDwtIHJlcG9ydGluZ19ndWlkZV9jb3VudCAlPiUgDQogIG11dGF0ZShyZXBvcnRpbmdfc3RhbmRhcmRzX3R5cGUgPSBpZmVsc2Uobjw9IDIsICJPdGhlciBndWlkZWxpbmUiLCBhcy5jaGFyYWN0ZXIocmVwb3J0aW5nX3N0YW5kYXJkc190eXBlKSkpICU+JSANCiAgZ3JvdXBfYnkocmVwb3J0aW5nX3N0YW5kYXJkc190eXBlKSAlPiUNCiAgc3VtbWFyaXNlKG4gPSBzdW0obikpDQoNCiMgR3JvdXBpbmcgYmlhcyBhc3Nlc3NtZW50IHZpc3VhbGl6YXRpb24gdHlwZXMgYW5kIHN1bW1pbmcgdGhlIGNvdW50cw0KYmlhc192aXN1YWxpemF0aW9uX2NvdW50IDwtIGJpYXNfdmlzdWFsaXphdGlvbl9jb3VudCAlPiUgDQogIG11dGF0ZShiaWFzX2Fzc2Vzc21lbnRfdmlzdWFsaXphdGlvbiA9IGlmX2Vsc2UoYmlhc19hc3Nlc3NtZW50X3Zpc3VhbGl6YXRpb24gJWluJSBjKCJkb2kgcGxvdCIsICJ0cmltIGFuZCBmaWxsIiwgIkZ1bm5lbCBwbG90IiksICJCaWFzIHZpc3VhbGl6YXRpb24iLCBiaWFzX2Fzc2Vzc21lbnRfdmlzdWFsaXphdGlvbikpICU+JSANCiAgZ3JvdXBfYnkoYmlhc19hc3Nlc3NtZW50X3Zpc3VhbGl6YXRpb24pICU+JQ0KICBzdW1tYXJpc2UobiA9IHN1bShuKSkNCg0KIyBDb21iaW5lIHRoZSBkYXRhIGZyYW1lcyBhbmQgdW5pdGUgdGhlIG1ldGhvZG9sb2d5IHR5cGVzDQpkZiA8LSBiaW5kX3Jvd3MoDQogIGRhdGFiYXNlX2NvdW50ICU+JSBtdXRhdGUobWV0aG9kb2xvZ3lfdHlwZSA9ICdEYXRhYmFzZSBTZWFyY2gnKSwNCiAgZWZmZWN0c2l6ZV9jb3VudCAlPiUgbXV0YXRlKG1ldGhvZG9sb2d5X3R5cGUgPSAnRWZmZWN0IFNpemUnKSwNCiAgc29mdHdhcmVfY291bnQgJT4lICBtdXRhdGUobWV0aG9kb2xvZ3lfdHlwZSA9ICJTb2Z0d2FyZSIpLA0KICBoZXRlcm9nZW5laXR5X2NvdW50ICU+JSBtdXRhdGUobWV0aG9kb2xvZ3lfdHlwZSA9ICJIZXRlcm9nZW5laXR5IiksDQogIHNlbnNpdGl2aXR5X2NvdW50ICU+JSBtdXRhdGUobWV0aG9kb2xvZ3lfdHlwZSA9ICJTZW5zaXRpdml0eV9BbmFseXNpcyIpLA0KICBiaWFzX21ldGhvZF9jb3VudCAlPiUgIG11dGF0ZShtZXRob2RvbG9neV90eXBlID0gIkJpYXMgQXNzZXNzbWVudCIpLA0KICByb2JfbWV0aG9kX2NvdW50ICU+JSBtdXRhdGUobWV0aG9kb2xvZ3lfdHlwZSA9ICJSaXNrICBvZiBCaWFzIiksIA0KICMgdmlzdWFsaXphdGlvbl9jb3VudCAlPiUgbXV0YXRlKG1ldGhvZG9sb2d5X3R5cGUgPSAiVmlzdWFsaXphdGlvbiIpLA0KICByZXBvcnRpbmdfZ3VpZGVfY291bnQgJT4lICBtdXRhdGUobWV0aG9kb2xvZ3lfdHlwZSA9ICJSZXBvcnRpbmcgR3VpZGUiKSwNCiAgYmlhc192aXN1YWxpemF0aW9uX2NvdW50ICU+JSAgbXV0YXRlKG1ldGhvZG9sb2d5X3R5cGUgPSAiQmlhcyBBc3Nlc3NtZW50IikNCikgJT4lIA0KIHVuaXRlKG1ldGhvZG9sb2d5X3R5cGVfc3BlY2lmaWMsIA0KICAgICAgIGRhdGFiYXNlX3NlYXJjaCwgDQogICAgICAgZWZmZWN0X3NpemUsICANCiAgICAgICBzb2Z0d2FyZV9hbmFseXNpcywNCiAgICAgICBoZXRlcm9nZW5laXR5X2Fzc2Vzc21lbnRfbWV0aG9kLCANCiAgICAgICBzZW5zaXRpdml0eV9hbmFseXNpc19tZXRob2QsIA0KICAgICAgIGJpYXNfYXNzZXNzbWVudF9tZXRob2QsDQogICAgICAgcm9iX2Fzc2Vzc21lbnRfbWV0aG9kLCANCiAgICAgICMgdmlzdWFsaXphdGlvbl9tZXRob2QsIA0KICAgICAgIHJlcG9ydGluZ19zdGFuZGFyZHNfdHlwZSwgDQogICAgICAgYmlhc19hc3Nlc3NtZW50X3Zpc3VhbGl6YXRpb24sDQogICAgICAgcmVtb3ZlID0gVFJVRSwgbmEucm0gPSBUUlVFKQ0KDQoNCg0KIyBQcmVwYXJpbmcgdGhlIGVkZ2VzIGRhdGFmcmFtZSBmb3IgY3JlYXRpbmcgdGhlIGdyYXBoDQplZGdlcyA8LSBkZiAlPiUNCiAgcmVuYW1lKGZyb20gPSBtZXRob2RvbG9neV90eXBlLCB0byA9IG1ldGhvZG9sb2d5X3R5cGVfc3BlY2lmaWMsIHNpemUgPSBuKSAlPiUNCiAgc2VsZWN0KGMoZnJvbSx0byxzaXplKSkgJT4lDQogIGFzLmRhdGEuZnJhbWUoKQ0KDQojIFByZXBhcmluZyB0aGUgdmVydGljZXMgZGF0YWZyYW1lIGZvciBjcmVhdGluZyB0aGUgZ3JhcGgNCnZlcnRpY2VzIDwtIGRmICAlPiUNCiAgcmVuYW1lKG5hbWUgPSBtZXRob2RvbG9neV90eXBlX3NwZWNpZmljLCBzaXplID0gbikgJT4lDQogIHNlbGVjdChjKG5hbWUsc2l6ZSkpICU+JQ0KICBhcy5kYXRhLmZyYW1lKCkNCg0KIyBBcHBlbmRpbmcgdW5pcXVlICdmcm9tJyB2YWx1ZXMgdG8gdmVydGljZXMgYW5kIHRoZWlyIGNvcnJlc3BvbmRpbmcgc3VtbWVkIHNpemVzDQp2ZXJ0aWNlc1sobnJvdyhlZGdlcykrMSk6KG5yb3coZWRnZXMpK2xlbmd0aCh1bmlxdWUoZWRnZXMkZnJvbSkpKSwxXSA8LSB1bmlxdWUoZWRnZXMkZnJvbSkNCk4gPC0gYWdncmVnYXRlKGVkZ2VzJHNpemUsIGxpc3QoZWRnZXMkZnJvbSksIEZVTj1zdW0pDQp2ZXJ0aWNlc1sobnJvdyhlZGdlcykrMSk6KG5yb3coZWRnZXMpK2xlbmd0aCh1bmlxdWUoZWRnZXMkZnJvbSkpKSwyXSA8LSBOJHgNCg0KIyBDcmVhdGluZyBhIGdyYXBoIG9iamVjdCBmcm9tIHRoZSBlZGdlcyBhbmQgdmVydGljZXMgZGF0YWZyYW1lcw0KbXlncmFwaCA8LSBncmFwaF9mcm9tX2RhdGFfZnJhbWUoZWRnZXMsIHZlcnRpY2VzID0gdmVydGljZXMpDQoNCiMgUGxvdHRpbmcgdGhlIGdyYXBoIHVzaW5nIGEgJ2NpcmNsZXBhY2snIGxheW91dCwgYWRkaW5nIGxhYmVscyBhbmQgYWRqdXN0aW5nIGFlc3RoZXRpY3MNCmZpZzIgPC0gZ2dyYXBoKG15Z3JhcGgsIGxheW91dCA9ICdjaXJjbGVwYWNrJywgd2VpZ2h0ID0gc2l6ZSkgKyANCiAgICBnZW9tX25vZGVfY2lyY2xlKGFlcyhmaWxsID0gYXMuZmFjdG9yKGRlcHRoKSksIGNvbG9yID0gTkEsIGFscGhhID0gMC41KSArDQogICAgZ2VvbV9ub2RlX3RleHQoYWVzKGxhYmVsID0gbmFtZSwgZmlsdGVyID0gbGVhZiwgc2l6ZSA9IDIpLCB2anVzdCA9IC0wLjMsIGZvbnRmYWNlID0gImJvbGQiKSArDQogICAgZ2VvbV9ub2RlX3RleHQoYWVzKGxhYmVsID0gcGFzdGUwKCIoIiwgc2l6ZSwgIikiKSwgZmlsdGVyID0gbGVhZiwgc2l6ZSA9IDIpLCB2anVzdCA9IDEsIGZvbnRmYWNlID0gImJvbGQiKSArDQogICAgdGhlbWVfdm9pZCgpICsNCiAgICB0aGVtZShsZWdlbmQucG9zaXRpb24gPSAibm9uZSIpICsNCiAgICBzY2FsZV9maWxsX21hbnVhbCh2YWx1ZXMgPSBjKCIjMWI5ZTc3IiwgIiNFNzI5OEEiKSkNCg0KDQpmaWcyDQpnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWcyLnBkZiIpLCB3aWR0aCA9IDIxLCBoZWlnaHQgPSAxNSwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCmdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZzIuanBnIiksIHdpZHRoID0gMjEsIGhlaWdodCA9IDE1LCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KDQpgYGANCg0KDQojIyBGaWd1cmUgMw0KVGhlIGF2ZXJhZ2UgcmVwb3J0aW5nIHF1YWxpdHkgYW5kIHJpZ291ciBvZiBtZXRhLWFuYWx5c2lzIGFjY29yZGluZyB0byBDRUVTQVQgMi4xIChXb29kY29jayBldCBhbC4sIDIwMTQpLiBHb2xkIGlzIHJlZ2FyZCBhcyB0aGUgaGlnaGVzdCBzY29yZSwgZ3JlZW4gaXMgc2Vjb25kIGhpZ2hlc3Qgc2NvcmUsIGFtYmVyIGlzIHNlY29uZC1sb3dlc3Qgc2NvcmUsIGFuZCByZWQgaXMgdGhlIGxvd2VzdCBzY29yZS4gQWxsIENFRVNBVCAyLjEgaXRlbXMgYWxvbmcgd2l0aCBvdXIgaW50ZXJwcmV0YXRpb24gYXJlIHByb3ZpZGVkIGluIHRoZSBzdXBwbGVtZW50YXJ5IGZpbGUgeC4NCmBgYHtyLCBmaWcud2lkdGg9MjUsIGZpZy5oZWlnaHQ9MTV9DQojIFN0YXJ0IHRoZSBkYXRhIG1hbmlwdWxhdGlvbg0KcGVyY2VudF9jZWVzYXRfc2NvcmUgPC0gc2QgJT4lDQogIGZpbHRlcighaXMubmEoYXV0aG9yX3llYXIpKSAlPiUNCiAgc2VsZWN0KHN0dWRpZXMgPSBhdXRob3JfeWVhciwgc3RhcnRzX3dpdGgoIkNFRSIpKSAlPiUNCiAgbmEub21pdCgpICU+JQ0KICBwaXZvdF9sb25nZXIoY29scyA9IC1zdHVkaWVzLCBuYW1lc190byA9ICJxdWVzdGlvbiIsIHZhbHVlc190byA9ICJzY29yZSIpICU+JQ0KICBncm91cF9ieShxdWVzdGlvbiwgc2NvcmUpICU+JQ0KICBzdW1tYXJpc2UobiA9IG4oKSwgLmdyb3VwcyA9ICdkcm9wJykgJT4lDQogIG11dGF0ZShwZXJjZW50ID0gKG4vc3VtKG4pKSoxMDAsIA0KICAgICAgICAgYWNyb3NzKGMocXVlc3Rpb24sIHNjb3JlKSwgYXMuZmFjdG9yKSwNCiAgICAgICAgIHF1ZXN0aW9uID0gZmN0X3JlY29kZShxdWVzdGlvbiwgDQogICAgICAgICAgIGAxLjEgQXJlIHRoZSBlbGVtZW50cyBvZiB0aGUgcmV2aWV3IHF1ZXN0aW9uIGNsZWFyP2AgPSAiQ0VFU0FUMl8xLjEiLA0KICAgICAgICAgICBgMi4xIElzIHRoZXJlIGFuIGEtcHJpb3JpIG1ldGhvZCBwcm90b2NvbCBkb2N1bWVudD9gID0gIkNFRVNBVDJfMi4xIiwNCiAgICAgICAgICAgYDMuMS4gSXMgdGhlIGFwcHJvYWNoIHRvIHNlYXJjaGluZyBjbGVhcmx5IGRlZmluZWRzeXN0ZW1hdGljIGFuZFxudHJhbnNwYXJlbnQ/YCA9ICJDRUVTQVQyXzMuMSIsDQogICAgICAgICAgIGAzLjIuIElzIHRoZSBzZWFyY2ggY29tcHJlaGVuc2l2ZT9gID0gIkNFRVNBVDJfMy4yIiwNCiAgICAgICAgICAgYDQuMS4gQXJlIGVsaWdpYmlsaXR5IGNyaXRlcmlhIGNsZWFybHkgZGVmaW5lZD9gID0gIkNFRVNBVDJfNC4xIiwNCiAgICAgICAgICAgYDQuMi4gQXJlIGVsaWdpYmlsaXR5IGNyaXRlcmlhIGNvbnNpc3RlbnRseSBhcHBsaWVkIHRvIGFsbCBwb3RlbnRpYWxseSByZWxldmFudFxuYXJ0aWNsZXMgYW5kIHN0dWRpZXMgZm91bmQgZHVyaW5nIHRoZSBzZWFyY2g/YCA9ICJDRUVTQVQyXzQuMiIsDQogICAgICAgICAgIGA0LjMuIEFyZSBlbGlnaWJpbGl0eSBkZWNpc2lvbnMgdHJhbnNwYXJlbnRseSByZXBvcnRlZD9gID0gIkNFRVNBVDJfNC4zIiwNCiAgICAgICAgICAgYDUuMS4gRG9lcyB0aGUgcmV2aWV3IGNyaXRpY2FsbHkgYXBwcmFpc2UgZWFjaCBzdHVkeT9gID0gIkNFRVNBVDJfNS4xIiwNCiAgICAgICAgICAgYDUuMi4gRHVyaW5nIGNyaXRpY2FsIGFwcHJhaXNhbCB3YXMgYW4gZWZmb3J0IG1hZGUgdG8gbWluaW1pc2VcbnN1YmplY3Rpdml0eT9gID0gIkNFRVNBVDJfNS4yIiwNCiAgICAgICAgICAgYDYuMS4gSXMgdGhlIG1ldGhvZCBvZiBkYXRhIGV4dHJhY3Rpb24gZnVsbHkgZG9jdW1lbnRlZD9gID0gIkNFRVNBVDJfNi4xIiwNCiAgICAgICAgICAgYDYuMi4gQXJlIHRoZSBleHRyYWN0ZWQgZGF0YSByZXBvcnRlZCBmb3IgZWFjaCBzdHVkeT9gID0gIkNFRVNBVDJfNi4yIiwNCiAgICAgICAgICAgYDYuMy4gV2VyZSBleHRyYWN0ZWQgZGF0YSBjcm9zcyBjaGVja2VkIGJ5IG1vcmUgdGhhbiBvbmUgcmV2aWV3ZXI/YCA9ICJDRUVTQVQyXzYuMyIsDQogICAgICAgICAgIGA3LjEuIElzIHRoZSBjaG9pY2Ugb2Ygc3ludGhlc2lzIGFwcHJvYWNoIGFwcHJvcHJpYXRlP2AgPSAiQ0VFU0FUMl83LjEiLA0KICAgICAgICAgICBgNy4yLiBJcyBhIHN0YXRpc3RpY2FsIGVzdGltYXRlIG9mIHBvb2xlZCBlZmZlY3QgcHJvdmlkZWQgdG9nZXRoZXIgd2l0aFxubWVhc3VyZSBvZiB2YXJpYW5jZSBhbmQgaGV0ZXJvZ2VuZWl0eSBhbW9uZyBzdHVkaWVzP2AgPSAiQ0VFU0FUMl83LjIiLA0KICAgICAgICAgICBgNy4zIElzIHZhcmlhYmlsaXR5IGluIHRoZSBzdHVkeSBmaW5kaW5ncyBpbnZlc3RpZ2F0ZWQgYW5kIGRpc2N1c3NlZD9gID0gIkNFRVNBVDJfNy4zIiwNCiAgICAgICAgICAgYDguMSBIYXZlIHRoZSBhdXRob3JzIGNvbnNpZGVyZWQgbGltaXRhdGlvbnMgaW4gdGhlIHN5bnRoZXNpcz9gID0gIkNFRVNBVDJfOC4xIiksDQogICAgICAgICBxdWVzdGlvbiA9IGZhY3RvcihxdWVzdGlvbiwgbGV2ZWxzID0gcmV2KGxldmVscyhxdWVzdGlvbikpKSwNCiAgICAgICAgIHNjb3JlID0gZmFjdG9yKHNjb3JlLCBsZXZlbHMgPSBsZXZlbHMoc2NvcmUpW2MoNCwxLDMsMildKSkNCg0KDQoNCg0KZmlnMyA8LSBnZ3Bsb3QoZGF0YSA9IHBlcmNlbnRfY2Vlc2F0X3Njb3JlLCBhZXMoeCA9IHF1ZXN0aW9uLCB5ID0gcGVyY2VudCwgZmlsbCA9IHNjb3JlKSkgKw0KICBnZW9tX2NvbCh3aWR0aCA9IDAuNywgcG9zaXRpb24gPSAiZmlsbCIsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoYWVzKGxhYmVsID0gbiksIHBvc2l0aW9uID0gcG9zaXRpb25fZmlsbCh2anVzdCA9IDAuNSksIHNpemUgPSA3LCBmb250ZmFjZSA9ICJib2xkIikgKw0KICBjb29yZF9mbGlwKCkgKw0KICBndWlkZXMoZmlsbCA9IGd1aWRlX2xlZ2VuZChyZXZlcnNlID0gVFJVRSkpICsNCiAgc2NhbGVfZmlsbF9tYW51YWwodmFsdWVzID0gYygiI0ZGMDAwMCIsIiNGRkQ3MDAiLCIjMDA4MDAwIiwgIiNEQUE1MjAiKSwgbmFtZSA9ICJTY29yZToiKSArDQogIHNjYWxlX3lfY29udGludW91cyhsYWJlbHMgPSBzY2FsZXM6OnBlcmNlbnQpICsNCiAgdGhlbWUocGFuZWwuZ3JpZC5tYWpvciA9IGVsZW1lbnRfYmxhbmsoKSwgDQogICAgICAgIHBhbmVsLmdyaWQubWlub3IgPSBlbGVtZW50X2JsYW5rKCksIA0KICAgICAgICBwYW5lbC5iYWNrZ3JvdW5kID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgICBheGlzLnRleHQueSA9IGVsZW1lbnRfdGV4dChzaXplID0gMjApLA0KICAgICAgICBheGlzLnRleHQueCA9IGVsZW1lbnRfdGV4dChzaXplID0gMjApLA0KICAgICAgICBheGlzLnRpdGxlLnggPSBlbGVtZW50X3RleHQoc2l6ZSA9IDI1KSwNCiAgICAgICAgYXhpcy50aXRsZS55ID0gZWxlbWVudF90ZXh0KHNpemUgPSAyNSksIA0KICAgICAgICAgIGxlZ2VuZC5wb3NpdGlvbiA9ICJub25lIikgKw0KICB5bGFiKCJQZXJjZW50YWdlIikgKyANCiAgeGxhYigiQ0VFU0FUIFF1ZXN0aW9uIikNCg0KDQoNCmdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZzMucGRmIiksIHdpZHRoID0gMjUsIGhlaWdodCA9IDE1LCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnMy5qcGciKSwgd2lkdGggPSAyNSwgaGVpZ2h0ID0gMTUsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQoNCmBgYA0KDQojIE9iamVjdGl2ZSAyIA0KVG8gZXhwbG9yZSB0aGUgdmFyaW91cyBjaGFyYWN0ZXJpc3RpY3Mgb2YgdGhlIG9yZ2Fub2NobG9yaW5lIHBlc3RpY2lkZXMgbGl0ZXJhdHVyZSBzdWNoIGFzIHRoZSBwZXN0aWNpZGVzIHVzZWQsIHRoZSBpbXBhY3RzIGVsaWNpdGVkIGluIHJlc3BvbnNlIGFuZCB0aGUgc3ViamVjdHMgdGhhdCB3ZXJlIGludmVzdGlnYXRlZC4NCg0KIyMgRmlndXJlIHMyNw0KQSBiYXIgcGxvdCBzaG93aW5nIHRoZSBwZXJjZW50YWdlIGFuZCB0b3RhbCBjb3VudCBvZiB0b3RhbCBvZiBwZXN0aWNpZGVzIGludmVzdGlnYXRlIGluIG1ldGEtYW5hbHlzaXMgaW52ZXN0aWdhdGluZyB0aGUgaW1wYWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiBOb3RlOiBzb21lIG1ldGEtYW5hbHlzaXMgbWF5IGNvbnRyaWJ1dGUgdG8gbXVsdGlwbGUgc2VjdGlvbnMgaWYgdGhlIHN0dWR5IGludm9sdmVzIG11bHRpcGxlIG9yZ2Fub2NobG9yaW5lIHBlc3RpY2lkZXMuIEZpbHRlcmVkIGZvciBwZXN0aWNpZGUgY291bnRzIGdyZWF0ZXIgdGhhbiA2LiANCmBgYHtyLGZpZy53aWR0aD0xNiwgZmlnLmhlaWdodD0xMH0NCiMgRnVuY3Rpb24gdG8gcmVwbGFjZSBsb25nIE9DUCBuYW1lcyB3aXRoIGFiYnJldmlhdGlvbnMNCnJlcGxhY2Vfb2NwIDwtIGZ1bmN0aW9uKGRmKSB7DQogIGRmICU+JSANCiAgICBtdXRhdGUob2NwID0gY2FzZV93aGVuKA0KICAgICAgIyBIQ0ggcmVsYXRlZCByZXBsYWNlbWVudHMNCiAgICAgIGdyZXBsKCJIZXhhY2hsb3JvY3ljbG9oZXhhbmUgXFwoSENIXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkhDSCIsDQogICAgICBncmVwbCgiYWxwaGEtSGV4YWNobG9yb2N5Y2xvaGV4YW5lIFxcKGFscGhhLUhDSFxcKSIsIG9jcCwgaWdub3JlLmNhc2UgPSBUUlVFKSB+ICLOsSAtIEhDSCIsDQogICAgICBncmVwbCgiYmV0YS1IZXhhY2hsb3JvY3ljbG9oZXhhbmUgXFwoYmV0YS1IQ0hcXCkiLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAizrIgLSBIQ0giLA0KICAgICAgZ3JlcGwoImdhbW1hLUhleGFjaGxvcm9jeWNsb2hleGFuZSBcXChnYW1tYS1IQ0hcXCkiLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAiTGluZGFuZSIsDQogICAgICAjIEREVCByZWxhdGVkIHJlcGxhY2VtZW50cw0KICAgICAgZ3JlcGwoIkRpY2hsb3JvZGlwaGVueWx0cmljaGxvcm9ldGhhbmUgXFwoRERUXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkREVCIsDQogICAgICBncmVwbCgicCxwLURpY2hsb3JvZGlwaGVueWx0cmljaGxvcm9ldGhhbmUgXFwocCxwLUREVFxcKSIsIG9jcCwgaWdub3JlLmNhc2UgPSBUUlVFKSB+ICJwLHAtRERUIiwNCiAgICAgIGdyZXBsKCJvLHAtRGljaGxvcm9kaXBoZW55bHRyaWNobG9yb2V0aGFuZSBcXChvLHAtRERUXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIm8scC1ERFQiLA0KICAgICAgIyBEREQgcmVsYXRlZCByZXBsYWNlbWVudHMNCiAgICAgIGdyZXBsKCJEaWNobG9yb2RpcGhlbnlsZGljaGxvcm9ldGhhbmUgXFwoREREXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkRERCIsDQogICAgICBncmVwbCgicCxwLURpY2hsb3JvZGlwaGVueWxkaWNobG9yb2V0aGFuZSBcXChwLHAtREREXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gInAscC1EREQiLA0KICAgICAgZ3JlcGwoIm8scC1EaWNobG9yb2RpcGhlbnlsZGljaGxvcm9ldGhhbmUgXFwobyxwLURERFxcKSIsIG9jcCwgaWdub3JlLmNhc2UgPSBUUlVFKSB+ICJvLHAtREREIiwNCiAgICAgICMgRERFIHJlbGF0ZWQgcmVwbGFjZW1lbnRzDQogICAgICBncmVwbCgiRGljaGxvcm9kaXBoZW55bGRpY2hsb3JvZXRoeWxlbmUgXFwoRERFXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkRERSIsDQogICAgICBncmVwbCgicCxwLURpY2hsb3JvZGlwaGVueWxkaWNobG9yb2V0aHlsZW5lIFxcKHAscC1EREVcXCkiLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAicCxwLURERSIsDQogICAgICBncmVwbCgibyxwLURpY2hsb3JvZGlwaGVueWxkaWNobG9yb2V0aHlsZW5lIFxcKG8scC1EREVcXCkiLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAibyxwLURERSIsDQogICAgICBUUlVFIH4gb2NwICAjIG5vIGNoYW5nZSBmb3IgYW55IG90aGVycw0KICAgICkpDQp9DQojIFRyYW5zZm9ybSB0aGUgZGF0YSANCm9jcF9jb3VudCA8LQ0KICBvY3AgJT4lIA0KICBzZXBhcmF0ZV9yb3dzKG9jcCwgc2VwID0gIixcXHMrIikgJT4lIA0KICByZXBsYWNlX29jcCAlPiUgDQogIGNvdW50KG9jcCkgJT4lIA0KICBmaWx0ZXIoIWlzLm5hKG9jcCkpICU+JSAjIGZpbHRlciBvdXQgTkEgDQogIGFycmFuZ2UoZGVzYyhuKSkgJT4lIA0KICBtdXRhdGUob2NwID0gaWZlbHNlKG4gPD0gNiwgIm90aGVyIE9DUCIsIGFzLmNoYXJhY3RlcihvY3ApKSkgJT4lIA0KIyBPdGhlciBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzIGluY2x1ZGU6IHRveGFwaGVuZSAobj02KSwgTWV0aG94eWNobG9yIChuPTYpLCBwLHAtREREIChuPTUpLCBvLHAtREREIChuPTUpLCBjaXMtQ2hsb3JkYW5lIChuPTUpLCB0cmFucz1DaGxvcmRhbmUgKG49NCksIEVuZG9zdWxmYW4gSUkgKG49NCksIEVuZG9zdWxmYW4gKG49MyksbyxwLURERCAobj0zKSwgY2lzLU5vbmFjaGxvciAobj0zKSB5LUNobG9yZGFuZSAobj0yKSwgQ2hsb3JvcGhlbm9sIChuPTIpLCBiZXRhLUJIQyAobj0yKSwgYWxwaGEtQ2hsb3JkYW5lIChuPTIpLCBUQ0REIChuPTEpLCBOb25hY2hsb3JlIChuPTEpLCBFbmRyaW4ga2V0b25lIChuPTEpLCBFbmRyaW4gQWxkZWh5ZGUgKG49MSksIEVuZG9zdWxmYW4gc3VsZmF0ZSAobj0xKSwgRGljb2ZvbCAobj0xKSwgZGVsdGEtSENIIChuPTEpLCBkZWx0YS1CSEMgKG49MSksIERERCAobj0xKSwgY2lzLUhlcHRhY2hsb3IgKG49MSksIGFscGhhLUJIQyAobj0xKS4NCiAgZ3JvdXBfYnkob2NwKSAlPiUgDQogIHN1bW1hcmlzZShuID1zdW0obikpDQoNCiMgQ2FsY3VsYXRlIHRoZSBwcm9wb3J0aW9uIGFuZCBwZXJjZW50YWdlIG9mIGVhY2ggT0NQDQpvY3BfcGN0IDwtIG9jcF9jb3VudCAlPiUNCiAgbXV0YXRlKHByb3BvcnRpb24gPSBuL3N1bShvY3BfY291bnQkbiksDQogICAgICAgICBwZXJjZW50YWdlID0gcHJvcG9ydGlvbioxMDApDQoNCiMgQ3JlYXRlIHRoZSBjb3VudCBwbG90IGZvciBPQ1BzDQpmaWdzMjcgPC0gb2NwX2NvdW50ICU+JQ0KICBnZ3Bsb3QoYWVzKHggPSBuLCB5ID0gcmVvcmRlcihvY3AsIG4pLCBmaWxsID0gIiMxYjllNzciKSkgKw0KICBnZW9tX2JhcihzdGF0ID0gImlkZW50aXR5Iiwgd2lkdGggPSAwLjgsIGFscGhhID0gMC43KSArDQogIGdlb21fdGV4dChhZXMobGFiZWwgPSBuLCB4ID0gbiAvIDIsIHkgPSByZW9yZGVyKG9jcCwgbikpLCBoanVzdCA9IDAuNSwgc2l6ZSA9IDYsIGNvbG9yID0gImJsYWNrIikgKw0KICBnZW9tX3RleHQoZGF0YSA9IG9jcF9wY3QsIGFlcyhsYWJlbCA9IHBhc3RlMCgiKCIsIHJvdW5kKHBlcmNlbnRhZ2UsIDEpLCAiJSkiKSwgeCA9IG4pLCANCiAgICAgICAgICAgIGhqdXN0ID0gLSAwLjEsIHNpemUgPSA2LCBjb2xvciA9ICJibGFjayIsIGZvbnRmYWNlID0gImJvbGQiKSArDQogIHNjYWxlX2ZpbGxfaWRlbnRpdHkoZ3VpZGUgPSAibm9uZSIpICsNCiAgc2NhbGVfeF9jb250aW51b3VzKG5hbWUgPSAiQXJ0aWNsZSBDb3VudCIsIGV4cGFuZCA9IGMoMCwgMCksIGxpbWl0cyA9IGMoMCwgbWF4KG9jcF9jb3VudCRuKSoxLjIpKSArDQogIGxhYnMoeSA9IE5VTEwpICsNCiAgdGhlbWVfbWluaW1hbCgpICsNCiAgdGhlbWUoYXhpcy50ZXh0LnkgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDE1KSwNCiAgICAgICAgYXhpcy50ZXh0LnggPSBlbGVtZW50X3RleHQoc2l6ZSA9IDE1KSwNCiAgICAgICAgYXhpcy5saW5lLnggPSBlbGVtZW50X2xpbmUoY29sb3IgPSAiZ3JheSIsIHNpemUgPSAwLjUpLA0KICAgICAgICBheGlzLmxpbmUueSA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgICAgYXhpcy50aWNrcy54ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgICBheGlzLnRpY2tzLnkgPSBlbGVtZW50X2JsYW5rKCksDQogICAgICAgIGF4aXMudGl0bGUueCA9IGVsZW1lbnRfdGV4dChzaXplID0gMjApLA0KICAgICAgICBheGlzLnRpdGxlLnkgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDIwKSwNCiAgICAgICAgcGFuZWwuZ3JpZC5tYWpvci55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgICBwYW5lbC5ncmlkLm1pbm9yLnkgPSBlbGVtZW50X2JsYW5rKCksDQogICAgICAgIGxlZ2VuZC5wb3NpdGlvbiA9ICJub25lIg0KICAgICAgICApDQpmaWdzMjcNCiAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczI3LnBkZiIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczI3LmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCmBgYA0KDQojIyBGaWd1cmUgczI4DQpBIGJhciBwbG90IHNob3dpbmcgdGhlIHBlcmNlbnRhZ2UgYW5kIHRvdGFsIGNvdW50IG9mIHRvdGFsIG9mIHN1YmplY3RzIGludmVzdGlnYXRlIGluIG1ldGEtYW5hbHlzaXMgaW52ZXN0aWdhdGluZyB0aGUgaW1wYWN0cyBvZiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLiBOb3RlOiBzb21lIG1ldGEtYW5hbHlzaXMgbWF5IGNvbnRyaWJ1dGUgdG8gbXVsdGlwbGUgc2VjdGlvbnMgaWYgdGhlIHN0dWR5IGludm9sdmVzIG11bHRpcGxlIHN1YmplY3RzDQpgYGB7cixmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIENhbGN1bGF0ZSB0b3RhbCBjb3VudCBmb3IgZWFjaCBjYXRlZ29yeQ0Kc3ViamVjdF9jb3VudCA8LSANCiAgc3ViICU+JSANCiAgICBzZXBhcmF0ZV9yb3dzKHN1YmplY3QsIHNlcCA9ICIsXFxzKyIpICU+JSANCiAgICBjb3VudChzdWJqZWN0KQ0KDQojIENhbGN1bGF0ZSBwcm9wb3J0aW9uIGFuZCBwZXJjZW50YWdlIGZvciBlYWNoIGNhdGVnb3J5DQpzdWJqZWN0X3BjdCA8LSBzdWJqZWN0X2NvdW50ICU+JQ0KICBtdXRhdGUocHJvcG9ydGlvbiA9IG4vc3VtKHN1YmplY3RfY291bnQkbiksDQogICAgICAgICBwZXJjZW50YWdlID0gcHJvcG9ydGlvbioxMDApDQoNCiMgQ3JlYXRlIHRoZSBjb3VudCBwbG90IGZvciBzdWJqZWN0cw0KZmlnczI4IDwtIHN1YmplY3RfY291bnQgJT4lDQogIGdncGxvdChhZXMoeCA9IG4sIHkgPSByZW9yZGVyKHN1YmplY3QsIG4pLCBmaWxsID0gIiMxYjllNzciKSkgKw0KICBnZW9tX2JhcihzdGF0ID0gImlkZW50aXR5Iiwgd2lkdGggPSAwLjggLCBhbHBoYSA9IDAuNykgKw0KICBnZW9tX3RleHQoYWVzKGxhYmVsID0gbiwgeCA9IG4gLyAyLCB5ID0gcmVvcmRlcihzdWJqZWN0LCBuKSksIGhqdXN0ID0gMC41LCBzaXplID0gNywgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChkYXRhID0gc3ViamVjdF9wY3QsIGFlcyhsYWJlbCA9IHBhc3RlMCgiKCIsIHJvdW5kKHBlcmNlbnRhZ2UsIDEpLCAiJSkiKSwgeCA9IG4pLCANCiAgICAgICAgICAgIGhqdXN0ID0gLTAuMSwgc2l6ZSA9IDYsIGNvbG9yID0gImJsYWNrIiwgZm9udGZhY2UgPSAiYm9sZCIpICsNCiAgc2NhbGVfZmlsbF9pZGVudGl0eShndWlkZSA9ICJub25lIikgKw0KICBzY2FsZV94X2NvbnRpbnVvdXMobmFtZSA9ICJBcnRpY2xlIENvdW50IiwgZXhwYW5kID0gYygwLCAwKSwgbGltaXRzID0gYygwLCBtYXgoc3ViamVjdF9jb3VudCRuKSoxLjEpKSArDQogIGxhYnMoeSA9IE5VTEwpICsNCiAgdGhlbWVfbWluaW1hbCgpICsNCiAgdGhlbWUoYXhpcy50ZXh0LnkgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDE1KSwNCiAgICAgICAgYXhpcy50ZXh0LnggPSBlbGVtZW50X3RleHQoc2l6ZSA9IDE1KSwNCiAgICAgICAgYXhpcy5saW5lLnggPSBlbGVtZW50X2xpbmUoY29sb3IgPSAiZ3JheSIsIHNpemUgPSAwLjUpLA0KICAgICAgICBheGlzLmxpbmUueSA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgICAgYXhpcy50aWNrcy54ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgICBheGlzLnRpY2tzLnkgPSBlbGVtZW50X2JsYW5rKCksDQogICAgICAgIGF4aXMudGl0bGUueCA9IGVsZW1lbnRfdGV4dChzaXplID0gMjApLA0KICAgICAgICBheGlzLnRpdGxlLnkgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDIwKSwNCiAgICAgICAgcGFuZWwuZ3JpZC5tYWpvci55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgICBwYW5lbC5ncmlkLm1pbm9yLnkgPSBlbGVtZW50X2JsYW5rKCksDQogICAgICAgIGxlZ2VuZC5wb3NpdGlvbiA9ICJub25lIg0KICAgICAgICApDQoNCmZpZ3MyOA0KIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZ3MyOC5wZGYiKSwgd2lkdGggPSAxNiwgaGVpZ2h0ID0gMTAsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczI4LmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCmBgYA0KDQojIyBGaWd1cmUgczI5IA0KQSBiYXIgcGxvdCBzaG93aW5nIHRoZSBwZXJjZW50YWdlIGFuZCB0b3RhbCBjb3VudCBvZiB0b3RhbCBvZiBzdWJqZWN0cyBpbnZlc3RpZ2F0ZSBpbiBtZXRhLWFuYWx5c2lzIGludmVzdGlnYXRpbmcgdGhlIGltcGFjdHMgb2Ygb3JnYW5vY2hsb3JpbmUgcGVzdGljaWRlcy4gTm90ZTogc29tZSBtZXRhLWFuYWx5c2lzIG1heSBjb250cmlidXRlIHRvIG11bHRpcGxlIHNlY3Rpb25zIGlmIHRoZSBzdHVkeSBpbnZvbHZlcyBtdWx0aXBsZSBzdWJqZWN0cy4gRmlsdGVyZWQgZm9yIGltcGFjdCBjb3VudHMgZ3JlYXRlciB0aGFuIDEuIA0KYGBge3IsZmlnLndpZHRoPTE2LCBmaWcuaGVpZ2h0PTEwfQ0KIyBDYWxjdWxhdGUgdG90YWwgY291bnQgZm9yIGVhY2ggY2F0ZWdvcnkNCmltcGFjdF9jb3VudCA8LSANCiAgaW0gJT4lIA0KICAgIHNlcGFyYXRlX3Jvd3MoaW1wYWN0LCBzZXAgPSAiLFxccysiKSAlPiUgDQogICAgY291bnQoaW1wYWN0KSAlPiUgDQogIGZpbHRlcihpbXBhY3QgIT0gIk5BIikgJT4lDQogIG11dGF0ZShpbXBhY3QgPSBpZmVsc2Uobjw9IDEsICJvdGhlciIsIGFzLmNoYXJhY3RlcihpbXBhY3QpKSkgJT4lIA0KICAgIGdyb3VwX2J5KGltcGFjdCkgJT4lDQogIHN1bW1hcmlzZShuID0gc3VtKG4pKQ0KDQojIENhbGN1bGF0ZSBwcm9wb3J0aW9uIGFuZCBwZXJjZW50YWdlIGZvciBlYWNoIGNhdGVnb3J5DQppbXBhY3RfcGN0IDwtIGltcGFjdF9jb3VudCAlPiUNCiAgbXV0YXRlKHByb3BvcnRpb24gPSBuL3N1bShpbXBhY3RfY291bnQkbiksDQogICAgICAgICBwZXJjZW50YWdlID0gcHJvcG9ydGlvbioxMDApDQoNCiMgQ3JlYXRlIHRoZSBjb3VudCBwbG90IGZvciBpbXBhY3RzIA0KZmlnczI5IDwtIGltcGFjdF9jb3VudCAlPiUNCiAgZ2dwbG90KGFlcyh4ID0gbiwgeSA9IHJlb3JkZXIoaW1wYWN0LCBuKSwgZmlsbCA9ICIjMWI5ZTc3IikpICsNCiAgZ2VvbV9iYXIoc3RhdCA9ICJpZGVudGl0eSIsIHdpZHRoID0gMC44ICwgYWxwaGEgPSAwLjcpICsNCiAgZ2VvbV90ZXh0KGFlcyhsYWJlbCA9IG4sIHggPSBuIC8gMiwgeSA9IHJlb3JkZXIoaW1wYWN0LCBuKSksIGhqdXN0ID0gMC41LCBzaXplID0gNywgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChkYXRhID0gaW1wYWN0X3BjdCwgYWVzKGxhYmVsID0gcGFzdGUwKCIoIiwgcm91bmQocGVyY2VudGFnZSwgMSksICIlKSIpLCB4ID0gbiksIA0KICAgICAgICAgICAgaGp1c3QgPSAtMC4xLCBzaXplID0gNiwgY29sb3IgPSAiYmxhY2siLCBmb250ZmFjZSA9ICJib2xkIikgKw0KICBzY2FsZV9maWxsX2lkZW50aXR5KGd1aWRlID0gIm5vbmUiKSArDQogIHNjYWxlX3hfY29udGludW91cyhuYW1lID0gIkFydGljbGUgQ291bnQiLCBleHBhbmQgPSBjKDAsIDApLCBsaW1pdHMgPSBjKDAsIG1heChpbXBhY3RfY291bnQkbikqMS4xKSkgKw0KICBsYWJzKHkgPSBOVUxMKSArDQogIHRoZW1lX21pbmltYWwoKSArDQogIHRoZW1lKGF4aXMudGV4dC55ID0gZWxlbWVudF90ZXh0KHNpemUgPSAxNSksDQogICAgICAgIGF4aXMudGV4dC54ID0gZWxlbWVudF90ZXh0KHNpemUgPSAxNSksDQogICAgICAgIGF4aXMubGluZS54ID0gZWxlbWVudF9saW5lKGNvbG9yID0gImdyYXkiLCBzaXplID0gMC41KSwNCiAgICAgICAgYXhpcy5saW5lLnkgPSBlbGVtZW50X2JsYW5rKCksDQogICAgICAgIGF4aXMudGlja3MueCA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgICAgYXhpcy50aWNrcy55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgICBheGlzLnRpdGxlLnggPSBlbGVtZW50X3RleHQoc2l6ZSA9IDIwKSwNCiAgICAgICAgYXhpcy50aXRsZS55ID0gZWxlbWVudF90ZXh0KHNpemUgPSAyMCksDQogICAgICAgIHBhbmVsLmdyaWQubWFqb3IueSA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgICAgcGFuZWwuZ3JpZC5taW5vci55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgICBsZWdlbmQucG9zaXRpb24gPSAibm9uZSINCiAgICAgICAgKQ0KDQpmaWdzMjkNCg0KICBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMjkucGRmIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KICBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMjkuanBnIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KDQpgYGANCg0KIyMgRmlndXJlIHMzMA0KQSBiYXIgcGxvdCBzaG93aW5nIHRoZSBwZXJjZW50YWdlIGFuZCB0b3RhbCBjb3VudCBvZiB0b3RhbCBvZiBpbXBhY3QgY2F0ZWdvcmllcyBpbnZlc3RpZ2F0ZWQgaW4gbWV0YS1hbmFseXNpcyBpbnZlc3RpZ2F0aW5nIHRoZSBpbXBhY3RzIG9mIG9yZ2Fub2NobG9yaW5lIHBlc3RpY2lkZXMuIA0KTm90ZTogc29tZSBtZXRhLWFuYWx5c2lzIG1heSBjb250cmlidXRlIHRvIG11bHRpcGxlIHNlY3Rpb25zIGlmIHRoZSBzdHVkeSBpbnZvbHZlcyBtdWx0aXBsZSBpbXBhY3RzDQpgYGB7cixmaWcud2lkdGg9MTYsIGZpZy5oZWlnaHQ9MTB9DQojIENyZWF0ZSBhIGNvbGx1bW4gZm9yIGJyb2FkIGltcGFjdHMNCmltIDwtIGltICU+JQ0KICAgICAgICBzZXBhcmF0ZV9yb3dzKGltcGFjdCwgc2VwID0gIixcXHMrIikgJT4lIA0KICBtdXRhdGUoaW1wYWN0X2Jyb2FkID0gY2FzZV93aGVuKA0KICAgIGltcGFjdCAlaW4lIGMoInBhcmtpbnNvbnMgZGlzZWFzZSIsICJhbHpoZWltZXJzIGRpc2Vhc2UiLCAiYXV0aXNtIHNwZWN0cnVtIGRpc29yZGVyIiwgImJyYWluIHR1bW91ciIsICJhbXlvdHJvcGhpYyBsYXRlcmFsIHNjbGVyb3NpcyIgKSB+ICJOZXVyb2xvZ2ljYWwiLA0KICAgIGltcGFjdCAlaW4lIGMoImNvbmNlbnRyYXRpb24iLCAiY29udGFtaW5hdGlvbiIpIH4gIkNvbmNlbnRyYXRpb24iLA0KICAgIGltcGFjdCAlaW4lIGMoImRpYWJldGVzIiwgInRoeXJvaWQgZnVuY3Rpb24iLCAiaHlwZXJ0ZW5zaW9uIiwgImVuZG9tZXRyaW9zaXMiKSB+ICJFbmRvY3JpbmUiLA0KICAgIGdyZXBsKCJjYW5jZXIiLCBpbXBhY3QsIGlnbm9yZS5jYXNlID0gVFJVRSkgfCBpbXBhY3QgJWluJSBjKCJsZXVrZW1pYSIsICJseW1waG9tYSIsICJtdWx0aXBsZSBteWVsb21hIiwgIm5ldXJvYmxhc3RvbWEiKSB+ICJDYXJjaW5vZ2VuIiwNCiAgICBpbXBhY3QgJWluJSBjKCJyZXNwaXJhdG9yeSBoZWFsdGgiLCAiY2FyZGlvdmFzY3VsYXIgZGlzZWFzZSIsICJhc3RobWEiLCAicHJvbG9uZ2VkIGJyYWR5Y2FyZGlhIikgfiAiQ2FyZGlvdmFzY3VsYXIiLA0KICMgICBpbXBhY3QgJWluJSBjKCJiaXJ0aCBvdXRjb21lcyIsICJiaXJ0aCB3ZWlnaHQiLCAicHJldGVybSBiaXJ0aCIpIH4gIkJpcnRoIiwNCiAgICBpbXBhY3QgJWluJSBjKCJvYmVzaXR5IiwgImFkaXBvc2l0eSIpIH4gIk9iZXNpdHkiLA0KICAgIGltcGFjdCAlaW4lIGMoInNwZXJtIHF1YWxpdHkiLCAibmV1cm9ibGFzdG9tYSIsICJoeXBvc3BhZGlhcyIsICJjcnlwdG9jaGlkaXNtIiwgInJlcHJvZHVjdGl2ZSBzeXN0ZW0iKSB+ICJSZXByb2R1Y3Rpb24iLA0KICAgIFRSVUUgfiAiT3RoZXIgSW1wYWN0Ig0KICApKQ0KDQoNCiMgQ2FsY3VsYXRlIHRvdGFsIGNvdW50IGZvciBlYWNoIGNhdGVnb3J5DQppbXBhY3RfY291bnRfYnJvYWQgPC0gDQogIGltICU+JSANCiAgICBzZXBhcmF0ZV9yb3dzKGltcGFjdF9icm9hZCwgc2VwID0gIixcXHMrIikgJT4lIA0KICAgIGNvdW50KGltcGFjdF9icm9hZCkgJT4lIA0KICBmaWx0ZXIoaW1wYWN0X2Jyb2FkICE9ICJOQSIpICU+JQ0KICAgIGdyb3VwX2J5KGltcGFjdF9icm9hZCkgJT4lDQogIHN1bW1hcmlzZShuID0gc3VtKG4pKQ0KDQojIENhbGN1bGF0ZSBwcm9wb3J0aW9uIGFuZCBwZXJjZW50YWdlIGZvciBlYWNoIGNhdGVnb3J5DQppbXBhY3RfcGN0X2Jyb2FkIDwtIGltcGFjdF9jb3VudF9icm9hZCAlPiUNCiAgbXV0YXRlKHByb3BvcnRpb24gPSBuL3N1bShpbXBhY3RfY291bnRfYnJvYWQkbiksDQogICAgICAgICBwZXJjZW50YWdlID0gcHJvcG9ydGlvbioxMDApDQoNCg0KIyBDcmVhdGUgdGhlIGNvdW50IHBsb3QgZm9yIGltcGFjdHMgDQpmaWdzMzAgPC0gaW1wYWN0X2NvdW50X2Jyb2FkICU+JQ0KICBnZ3Bsb3QoYWVzKHggPSBuLCB5ID0gcmVvcmRlcihpbXBhY3RfYnJvYWQsIG4pLCBmaWxsID0gIiMxYjllNzciKSkgKw0KICBnZW9tX2JhcihzdGF0ID0gImlkZW50aXR5Iiwgd2lkdGggPSAwLjggLCBhbHBoYSA9IDAuNykgKw0KICBnZW9tX3RleHQoYWVzKGxhYmVsID0gbiwgeCA9IG4gLyAyLCB5ID0gcmVvcmRlcihpbXBhY3RfYnJvYWQsIG4pKSwgaGp1c3QgPSAwLjUsIHNpemUgPSA3LCBjb2xvciA9ICJibGFjayIpICsNCiAgZ2VvbV90ZXh0KGRhdGEgPSBpbXBhY3RfcGN0X2Jyb2FkLCBhZXMobGFiZWwgPSBwYXN0ZTAoIigiLCByb3VuZChwZXJjZW50YWdlLCAxKSwgIiUpIiksIHggPSBuKSwgDQogICAgICAgICAgICBoanVzdCA9IC0wLjEsIHNpemUgPSA2LCBjb2xvciA9ICJibGFjayIsIGZvbnRmYWNlID0gImJvbGQiKSArDQogIHNjYWxlX2ZpbGxfaWRlbnRpdHkoZ3VpZGUgPSAibm9uZSIpICsNCiAgc2NhbGVfeF9jb250aW51b3VzKG5hbWUgPSAiQXJ0aWNsZSBDb3VudCIsIGV4cGFuZCA9IGMoMCwgMCksIGxpbWl0cyA9IGMoMCwgbWF4KGltcGFjdF9jb3VudF9icm9hZCRuKSoxLjEpKSArDQogIGxhYnMoeSA9IE5VTEwpICsNCiAgdGhlbWVfbWluaW1hbCgpICsNCiAgdGhlbWUoYXhpcy50ZXh0LnkgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDE1KSwNCiAgICAgICAgYXhpcy50ZXh0LnggPSBlbGVtZW50X3RleHQoc2l6ZSA9IDE1KSwNCiAgICAgICAgYXhpcy5saW5lLnggPSBlbGVtZW50X2xpbmUoY29sb3IgPSAiZ3JheSIsIHNpemUgPSAwLjUpLA0KICAgICAgICBheGlzLmxpbmUueSA9IGVsZW1lbnRfYmxhbmsoKSwNCiAgICAgICAgYXhpcy50aWNrcy54ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgICBheGlzLnRpY2tzLnkgPSBlbGVtZW50X2JsYW5rKCksDQogICAgICAgIGF4aXMudGl0bGUueCA9IGVsZW1lbnRfdGV4dChzaXplID0gMjApLA0KICAgICAgICBheGlzLnRpdGxlLnkgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDIwKSwNCiAgICAgICAgcGFuZWwuZ3JpZC5tYWpvci55ID0gZWxlbWVudF9ibGFuaygpLA0KICAgICAgICBwYW5lbC5ncmlkLm1pbm9yLnkgPSBlbGVtZW50X2JsYW5rKCksDQogICAgICAgIGxlZ2VuZC5wb3NpdGlvbiA9ICJub25lIg0KICAgICAgICApDQoNCmZpZ3MzMA0KDQogICBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMzAucGRmIiksIHdpZHRoID0gMTYsIGhlaWdodCA9IDEwLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KICAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczMwLmpwZyIpLCB3aWR0aCA9IDE2LCBoZWlnaHQgPSAxMCwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KYGBgDQoNCiMjIEZpZ3VyZSBzMzENCkFuIGFsbHV2aWFsIHBsb3Qgc2hvd2luZyB0aGUgcmVsYXRpb25zaGlwcyBiZXR3ZWVuIHRoZSBwZXN0aWNpZGUgb2YgZXhwb3N1cmUsIHRoZSBzdWJqZWN0IGJlaW5nIGV4cG9zZWQgYW5kIHRoZSBpbXBhY3Qgb2YgZXhwb3N1cmUgDQpgYGB7cixmaWcud2lkdGg9MTgsIGZpZy5oZWlnaHQ9MTJ9DQoNCiMgRnVuY3Rpb24gdG8gY2hhbmdlIE9DUCB0byBiZSBtb3JlIGdlbmVyYWwNCnJlcGxhY2Vfb2NwMiA8LSBmdW5jdGlvbihkZikgew0KICBkZiAlPiUgDQogIG11dGF0ZShvY3AgPSBjYXNlX3doZW4oDQogICAgZ3JlcGwoIkNobG9yZGFuZSIsIG9jcCwgaWdub3JlLmNhc2UgPSBUUlVFKSB+ICJDaGxvcmRhbmUiLCAgDQogICAgZ3JlcGwoIkVuZG9zdWxmYW4iLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAiRW5kb3N1bGZhbiIsIA0KICAgIGdyZXBsKCJOb25hY2hsb3IiLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAiTm9uYWNobG9yZSIsIA0KICAgIGdyZXBsKCJIZXB0YWNobG9yIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkhlcHRhY2hsb3IiLA0KICAgIGdyZXBsKCJUQ0REIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIlRDREQiLCANCiAgICBncmVwbCgiRW5kcmluIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkVuZHJpbiIsDQogICAgZ3JlcGwoIkhleGFjaGxvcm9iZW56ZW5lIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkhDSCIsDQogICAgZ3JlcGwoIkxpbmRhbmUiLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAiSENIIiwgDQogICAgZ3JlcGwoIkhleGFjaGxvcm9jeWNsb2hleGFuZSBcXChIQ0hcXCkiLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAiSENIIiwNCiAgICBncmVwbCgiYWxwaGEtSGV4YWNobG9yb2N5Y2xvaGV4YW5lIFxcKGFscGhhLUhDSFxcKSIsIG9jcCwgaWdub3JlLmNhc2UgPSBUUlVFKSB+ICJIQ0giLA0KICAgIGdyZXBsKCJiZXRhLUhleGFjaGxvcm9jeWNsb2hleGFuZSBcXChiZXRhLUhDSFxcKSIsIG9jcCwgaWdub3JlLmNhc2UgPSBUUlVFKSB+ICJIQ0giLA0KICAgIGdyZXBsKCJnYW1tYS1IZXhhY2hsb3JvY3ljbG9oZXhhbmUgXFwoZ2FtbWEtSENIXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkhDSCIsDQogICAgZ3JlcGwoIkRpY2hsb3JvZGlwaGVueWx0cmljaGxvcm9ldGhhbmUgXFwoRERUXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkREVCIsDQogICAgZ3JlcGwoInAscC1EaWNobG9yb2RpcGhlbnlsdHJpY2hsb3JvZXRoYW5lIFxcKHAscC1ERFRcXCkiLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAiRERUIiwNCiAgICBncmVwbCgibyxwLURpY2hsb3JvZGlwaGVueWx0cmljaGxvcm9ldGhhbmUgXFwobyxwLUREVFxcKSIsIG9jcCwgaWdub3JlLmNhc2UgPSBUUlVFKSB+ICJERFQiLA0KICAgIGdyZXBsKCJEaWNobG9yb2RpcGhlbnlsZGljaGxvcm9ldGhhbmUgXFwoREREXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkRERCIsDQogICAgZ3JlcGwoInAscC1EaWNobG9yb2RpcGhlbnlsZGljaGxvcm9ldGhhbmUgXFwocCxwLURERFxcKSIsIG9jcCwgaWdub3JlLmNhc2UgPSBUUlVFKSB+ICJEREQiLA0KICAgIGdyZXBsKCJvLHAtRGljaGxvcm9kaXBoZW55bGRpY2hsb3JvZXRoYW5lIFxcKG8scC1ERERcXCkiLCBvY3AsIGlnbm9yZS5jYXNlID0gVFJVRSkgfiAiREREIiwNCiAgICBncmVwbCgiRGljaGxvcm9kaXBoZW55bGRpY2hsb3JvZXRoeWxlbmUgXFwoRERFXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkRERSIsDQogICAgZ3JlcGwoInAscC1EaWNobG9yb2RpcGhlbnlsZGljaGxvcm9ldGh5bGVuZSBcXChwLHAtRERFXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkRERSIsDQogICAgZ3JlcGwoIm8scC1EaWNobG9yb2RpcGhlbnlsZGljaGxvcm9ldGh5bGVuZSBcXChvLHAtRERFXFwpIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpIH4gIkRERSIsDQogICAgVFJVRSB+IG9jcA0KICApKQ0KfQ0KIA0KDQojIFRyYW5zZm9ybSB0aGUgZGF0YSANCmFsbHV2aWFsIDwtIGltICU+JQ0KICBsZWZ0X2pvaW4ob2NwLCBieSA9ICJzdHVkeV9pZCIpICU+JQ0KICBsZWZ0X2pvaW4oc3ViLCBieSA9ICJzdHVkeV9pZCIpICU+JQ0KICBzZXBhcmF0ZV9yb3dzKHN1YmplY3QsIHNlcCA9ICIsXFxzKyIpICU+JSANCiAgc2VwYXJhdGVfcm93cyhvY3AsIHNlcCA9ICIsXFxzKyIpICU+JSANCiAgc2VwYXJhdGVfcm93cyhpbXBhY3RfYnJvYWQsIHNlcCA9ICIsXFxzKyIpICU+JQ0KICByZXBsYWNlX29jcDIoKSAlPiUNCiAgZmlsdGVyKCFncmVwbCgibm90IHJlcG9ydGVkIiwgb2NwLCBpZ25vcmUuY2FzZSA9IFRSVUUpKSAlPiUNCiAgZ3JvdXBfYnkob2NwLCBzdWJqZWN0LCBpbXBhY3RfYnJvYWQpICU+JQ0KICBzdW1tYXJpc2UoZnJlcSA9IG4oKSwgLmdyb3VwcyA9ICdkcm9wJykgJT4lDQogIGdyb3VwX2J5KG9jcCkgJT4lDQogIGZpbHRlcihzdW0oZnJlcSkgPiAxMCkgJT4lICANCiAgZ3JvdXBfYnkoaW1wYWN0X2Jyb2FkKSAlPiUgDQogIGZpbHRlcihzdW0oZnJlcSkgPiA1KSAlPiUgDQogIG11dGF0ZShzdWJqZWN0ID0gZmFjdG9yKHN1YmplY3QsIGxldmVscyA9IGMoIkVudmlyb25tZW50IiwgIk5vbi1odW1hbiBhbmltYWwiLCAiSHVtYW4iKSwgb3JkZXJlZCA9IFRSVUUpKQ0KDQoNCmZpZ3MzMSA8LSBhbGx1dmlhbCAlPiUgDQogIGdncGxvdCgNCiAgICAgICBhZXMoYXhpczEgPSBvY3AsIGF4aXMyID0gc3ViamVjdCwgYXhpczMgPSBpbXBhY3RfYnJvYWQsIHkgPSBmcmVxKSkgKw0KICBzY2FsZV94X2Rpc2NyZXRlKGxpbWl0cyA9IGMoIk9yZ2Fub2NobG9yaW5lIFBlc3RpY2lkZSIsICJTdWJqZWN0IiwgIkltcGFjdCIpLCBleHBhbmQgPSBjKC4wNSwgLjEwKSkgKw0KICB4bGFiKCJWYXJpYWJsZXMiKSArDQogIHlsYWIoIkZyZXF1ZW5jeSIpICsgIA0KICBnZW9tX2FsbHV2aXVtKGFlcyhmaWxsID0gc3ViamVjdCkpICsNCiAgZ2VvbV9zdHJhdHVtKHdpZHRoID0gMS8yLCBmaWxsID0gIndoaXRlIiwgY29sb3IgPSAiYmxhY2siKSArDQogIGdlb21fdGV4dChzdGF0ID0gInN0cmF0dW0iLCBhZXMobGFiZWwgPSBhZnRlcl9zdGF0KHN0cmF0dW0pKSwgc2l6ZSA9IDUsIGZvbnRmYWNlID0gImJvbGQiKSArICANCiAgdGhlbWVfbWluaW1hbCgpICsNCiAgdGhlbWUoYXhpcy50ZXh0PWVsZW1lbnRfdGV4dChzaXplPTE1KSwgIA0KICAgICAgICBheGlzLnRpdGxlPWVsZW1lbnRfdGV4dChzaXplPTIwKSwNCiAgICAgICAgbGVnZW5kLnBvc2l0aW9uPSJub25lIiwNCiAgICAgICAgcGFuZWwuZ3JpZC5tYWpvciA9IGVsZW1lbnRfYmxhbmsoKSwgIA0KICAgICAgICBwYW5lbC5ncmlkLm1pbm9yID0gZWxlbWVudF9ibGFuaygpICANCiAgKSArIA0KICBzY2FsZV9maWxsX2JyZXdlcihwYWxldHRlID0gIkRhcmsyIiwgbmFtZSA9ICJTdWJqZWN0IENhdGVnb3J5IikNCg0KZmlnczMxDQoNCiAgICBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWdzMzEucGRmIiksIHdpZHRoID0xOCwgaGVpZ2h0ID0gMTIsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQogICAgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnczMxLmpwZyIpLCB3aWR0aCA9IDE4LCBoZWlnaHQgPSAxMiwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCg0KDQpgYGANCg0KDQojIyBGaWd1cmUNCiANCmBgYHtyLGZpZy53aWR0aD0yNSwgZmlnLmhlaWdodD0xNX0NCg0KIyBKb2luIHRoZSBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGUgZGV0YWlscyB3aXRoIHRoZSBpbXBhY3QgZGV0YWlscw0Kb2NwX2ltIDwtIGxlZnRfam9pbihvY3AsIGltICxzdWIsIGJ5ID0gInN0dWR5X2lkIikgDQoNCiMgU2VwYXJhdGUgcm93cyBpbiAib2NwX2ltIg0Kb2NwX2ltMSA8LSBzZXBhcmF0ZV9yb3dzKG9jcF9pbSwgb2NwICwgc2VwID0gIiwgIiwgY29udmVydCA9IFRSVUUpDQoNCg0KIyBHcm91cCBieSAib2NwIiBhbmQgImltcGFjdCIgYW5kIHN1bW1hcml6ZSBjb3VudA0Kb2NwX2ltX3N1bW1hcnkgPC0gb2NwX2ltMSAlPiUNCiAgbXV0YXRlKG9jcCA9IHN0cl90cmltKG9jcCksDQogICAgICAgICBpbXBhY3RfYnJvYWQgPSBzdHJfdHJpbShpbXBhY3RfYnJvYWQpKSAlPiUNCiAgICByZXBsYWNlX29jcDIoKSAlPiUgDQogIGdyb3VwX2J5KG9jcCwgaW1wYWN0X2Jyb2FkKSAlPiUNCiAgc3VtbWFyaXNlKGNvdW50ID0gbigpLCAuZ3JvdXBzID0gImRyb3AiKSANCg0KDQojIEZpbHRlciBmb3IgdG9wIDUgcGVzdGljaWRlcyANCnRvcF9wZXN0aWNpZGVzIDwtIG9jcF9pbV9zdW1tYXJ5ICU+JQ0KICBmaWx0ZXIob2NwICE9ICJub3QgcmVwb3J0ZWQiKSAlPiUNCiAgZ3JvdXBfYnkob2NwKSAlPiUNCiAgc3VtbWFyaXNlKHRvdGFsX2NvdW50ID0gc3VtKGNvdW50KSkgJT4lDQogIHRvcF9uKDgsIHRvdGFsX2NvdW50KSAlPiUNCiAgcHVsbChvY3ApIA0KDQoNCm9jcF9pbV9zdW1tYXJ5X2ZpbHRlcmVkIDwtIG9jcF9pbV9zdW1tYXJ5ICU+JQ0KICBmaWx0ZXIob2NwICVpbiUgdG9wX3Blc3RpY2lkZXMpDQoNCiMgQ3JlYXRlIGEgY2lyY2xlIHBsb3Qgd2l0aCBpbXBhY3Qgb24gdGhlIHgtYXhpcyBhbmQgb2NwIG9uIHRoZSB5LWF4aXMNCm9jcF9pbV9zdW1tYXJ5X2ZpbHRlcmVkICU+JSANCmdncGxvdChhZXMoeCA9IGZjdF9yZXYoZmN0X3Jlb3JkZXIoaW1wYWN0X2Jyb2FkLCBjb3VudCwgLmZ1biA9ICdzdW0nKSksDQogICAgICAgICAgIHkgPSBmY3RfcmVvcmRlcihvY3AsIGNvdW50LCAuZnVuID0gJ3N1bScpLA0KICAgICAgICAgICBzaXplID0gY291bnQsDQogICAgICAgICAgIGZpbGwgPSBjb3VudCkpICsNCiAgZ2VvbV9wb2ludChzaGFwZSA9IDIxLCBjb2xvciA9ICJ3aGl0ZSIpICsNCiAgZ2VvbV90ZXh0KGFlcyhsYWJlbCA9IGNvdW50KSwgc2l6ZSA9IDgsIGZvbnRmYWNlID0gImJvbGQiKSArICANCiAgc2NhbGVfZmlsbF9ncmFkaWVudChsb3cgPSAiIzk4RkI5OCIsIGhpZ2ggPSAiIzAwNjQwMCIpICsNCiAgbGFicyh4ID0gIkltcGFjdCIsDQogICAgICAgeSA9ICJPcmdhbm9jaGxvcmluZSBQZXN0aWNpZGUiLA0KICAgICAgIGZpbGwgPSAiQ291bnQiKSArDQogIHRoZW1lX21pbmltYWwoKSArDQogIHRoZW1lKA0KICAgICAgICBheGlzLnRpY2tzLnkgPSBlbGVtZW50X2JsYW5rKCksDQogICAgICAgIGF4aXMudGV4dC54ID0gZWxlbWVudF90ZXh0KHNpemUgPSAyMCksICANCiAgICAgICAgYXhpcy50ZXh0LnkgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDIwLCBoanVzdCA9IDEpLCAgDQogICAgICAgIGF4aXMudGl0bGUueCA9IGVsZW1lbnRfdGV4dChzaXplID0gMjUpLCAgDQogICAgICAgIGF4aXMudGl0bGUueSA9IGVsZW1lbnRfdGV4dChzaXplID0gMjUpLCAgDQogICAgICAgIGxlZ2VuZC5wb3NpdGlvbiA9ICJub25lIikgKw0KICBzY2FsZV9zaXplX2NvbnRpbnVvdXMocmFuZ2UgPSBjKDE1LCA0NSkpIA0KDQogIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZzMucGRmIiksIHdpZHRoID0gMjUsIGhlaWdodCA9IDE1LCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KICBnZ3NhdmUoaGVyZSgiZmlndXJlcyIsICJmaWczLmpwZyIpLCB3aWR0aCA9IDI1LCBoZWlnaHQgPSAxNSwgdW5pdHMgPSAiY20iLCBzY2FsZSA9IDIsIGRwaSA9IDgwMCkNCiAgDQpgYGANCg0KDQoNCiAtICoqT2JqZWN0aXZlIDQuCUJpYmxpb21ldHJpY3M6IEhvdyBpcyBzeW50aGVzaXplZCBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGUgZXZpZGVuY2UgY29ubmVjdGVkPyoqIFdlIHdpbGwgaW52ZXN0aWdhdGUgdGhlIGNvdW50cmllcyBhbmQgaW5zdGl0dXRpb25zIHRoYXQgYXJlIHByaW1hcmlseSBlbmdhZ2VkIGluIHNlY29uZGFyeSByZXNlYXJjaCBvbiBvcmdhbm9jaGxvcmluZSBwZXN0aWNpZGVzLCBhbmQgYW5hbHl6ZSB0aGUgbmV0d29ya3MgdGhhdCBleGlzdCBiZXR3ZWVuIHRoZW0uIEJ5IGRvaW5nIHNvLCB3ZSBob3BlIHRvIGdhaW4gaW5zaWdodHMgaW50byB0aGUgY29sbGFib3JhdGl2ZSByZWxhdGlvbnNoaXBzIGJldHdlZW4gZGlmZmVyZW50IGluc3RpdHV0aW9ucyBhbmQgaWRlbnRpZnkgYW55IHBhdHRlcm5zIG9yIHRyZW5kcyBpbiB0aGUgZGlzdHJpYnV0aW9uIG9mIHJlc2VhcmNoIGVmZm9ydHMuDQoNCmBgYHtyfQ0KZmlnNWEgPC0gYmlibGlvQW5hbHlzaXMoYmliX3NjbykNCnBsb3QoZmlnNWEpDQpgYGANCg0KIyMgZmlnNWMgLSB0aGVtYXRpYyBtYXAgYmFzZWQgb24ga2V5d29yZHMNCmBgYHtyfQ0KcGFyKG1mcm93PWMoMSwxKSwgbWFyPWMoMCwyLDAsMikpDQpmaWc1YyA8LSB0aGVtYXRpY01hcChiaWJfc2NvLCBmaWVsZCA9ICJJRCIsIG4gPSAxMDAwLCBtaW5mcmVxID0gNSwgc3RlbW1pbmcgPSBGQUxTRSwgc2l6ZSA9IDAuNSwgbi5sYWJlbHMgPSAxLCByZXBlbCA9IFRSVUUpDQpwbG90KGZpZzVjJG1hcCkNCg0KYGBgDQoNCiMjIGZpZyA1ZCAtIGF1dGhvciBjb2xsYWJvcmF0aW9uIG5ldHdvcmsNCmBgYHtyfQ0KTmV0TWF0cml4X2F1dGhvcnMgPC0gYmlibGlvTmV0d29yayhiaWJfc2NvLCBhbmFseXNpcyA9ICJjb2xsYWJvcmF0aW9uIiwgIG5ldHdvcmsgPSAiYXV0aG9ycyIsIHNlcCA9ICI7IikNCmZpZzVkIDwtIG5ldHdvcmtQbG90KE5ldE1hdHJpeF9hdXRob3JzLCAgbiA9IDEwMCwgDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIFRpdGxlID0gIkF1dGhvciBjb2xsYWJvcmF0aW9uIiwgDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHR5cGUgPSAiYXV0byIsIHNpemUgPSA0LCBzaXplLmNleCA9IFRSVUUsIA0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBlZGdlc2l6ZSA9IDEwLCBsYWJlbHNpemUgPSAxLjEpDQpgYGANCg0KIyMgZmlnNWUgLSBjb3VudHJ5IHB1YmxpY2F0aW9ucyBtYXANCmBgYHtyfQ0KIyBFeHRyYWN0IGNvdW50cnkgaW5mb3JtYXRpb24gZnJvbSB0aGUgIkFVMV9DTyIgYW5kICJBVV9DTyIgZmllbGRzIG9mIHRoZSAiYmliX3NjbyIgZGF0YXNldA0KYmlibWFwIDwtIG1ldGFUYWdFeHRyYWN0aW9uKGJpYl9zY28sIEZpZWxkID0gIkFVMV9DTyIsIHNlcCA9ICI7IikgDQpiaWJtYXAgPC0gbWV0YVRhZ0V4dHJhY3Rpb24oYmlibWFwLCBGaWVsZCA9ICJBVV9DTyIsIHNlcCA9ICI7IikgDQoNCiMgQ3JlYXRlIGEgZGF0YSBmcmFtZSB3aXRoIGNvdW50cyBvZiBhcnRpY2xlcyBmcm9tIGVhY2ggY291bnRyeQ0KZmlyc3Rjb3VudHJ5Y291bnRzIDwtIGJpYm1hcCAlPiUgDQogIGdyb3VwX2J5KEFVMV9DTykgJT4lIA0KICBjb3VudCgpICU+JSANCiAgZmlsdGVyKCFpcy5uYShBVTFfQ08pKSAgDQoNCiMgTG9hZCB3b3JsZCBtYXAgZGF0YSBhbmQgcmVtb3ZlIGNvdW50cmllcyB3aXRoIGxvbmdpdHVkZSA+MTgwIHRvIG1ha2UgYW4gZXF1YWwgcHJvamVjdGlvbi1saWtlIG1hcA0Kd29ybGRfbWFwIDwtIG1hcF9kYXRhKCJ3b3JsZCIpICU+JSANCiAgZmlsdGVyKCEgbG9uZyA+IDE4MCkNCg0KIyBGb3JtYXQgY291bnRyeSBuYW1lcyB0byBtYXRjaCByZWdpb25zIG9uIHRoZSB3b3JsZCBtYXANCmZpcnN0Y291bnRyeWNvdW50cyRyZWdpb24gPC0gc3RyX3RvX3RpdGxlKGZpcnN0Y291bnRyeWNvdW50cyRBVTFfQ08pDQpmaXJzdGNvdW50cnljb3VudHMkcmVnaW9uW2ZpcnN0Y291bnRyeWNvdW50cyRyZWdpb24gPT0gIlVzYSJdIDwtICJVU0EiIA0KZmlyc3Rjb3VudHJ5Y291bnRzJHJlZ2lvbltmaXJzdGNvdW50cnljb3VudHMkcmVnaW9uID09ICJLb3JlYSJdIDwtICJTb3V0aCBLb3JlYSINCg0KIyBKb2luIGNvdW50IGRhdGEgd2l0aCBtYXAgZGF0YSBhbmQgc2V0IG1pc3NpbmcgY291bnRzIHRvIHplcm8NCmVtcHR5bWFwIDwtIHRpYmJsZShyZWdpb24gPSB1bmlxdWUod29ybGRfbWFwJHJlZ2lvbiksIG4gPSByZXAoMCxsZW5ndGgodW5pcXVlKHdvcmxkX21hcCRyZWdpb24pKSkpDQpmdWxsbWFwIDwtIGxlZnRfam9pbihlbXB0eW1hcCwgZmlyc3Rjb3VudHJ5Y291bnRzLCBieSA9ICJyZWdpb24iKQ0KZnVsbG1hcCRuIDwtIGZ1bGxtYXAkbi54ICsgZnVsbG1hcCRuLnkNCmZ1bGxtYXAkbltpcy5uYShmdWxsbWFwJG4pXSA8LSAwDQoNCmZpZzUgPC0gZnVsbG1hcCAlPiUNCiAgZ2dwbG90KGFlcyhmaWxsID0gbiwgbWFwX2lkID0gcmVnaW9uKSkgKw0KICBnZW9tX21hcChtYXAgPSB3b3JsZF9tYXAsIGNvbG9yID0gImdyYXk1MCIpICsNCiAgZXhwYW5kX2xpbWl0cyh4ID0gd29ybGRfbWFwJGxvbmcsIHkgPSB3b3JsZF9tYXAkbGF0KSArDQogIGNvb3JkX21hcCgibWVyY2F0b3IiKSArDQogIHRoZW1lX21pbmltYWwoKSArDQogIHRoZW1lKA0KICAgIGF4aXMudGV4dCA9IGVsZW1lbnRfYmxhbmsoKSwgIA0KICAgIGF4aXMudGl0bGUgPSBlbGVtZW50X2JsYW5rKCksICANCiAgICBsZWdlbmQucG9zaXRpb24gPSAiYm90dG9tIiwNCiAgICBsZWdlbmQuYm94ID0gImhvcml6b250YWwiLCAgDQogICAgbGVnZW5kLmJveC5qdXN0ID0gImNlbnRlciIsICANCiAgICBsZWdlbmQubWFyZ2luID0gbWFyZ2luKHQgPSAxMCwgdW5pdCA9ICJwdCIpLCAgDQogICAgbGVnZW5kLnRleHQgPSBlbGVtZW50X3RleHQoc2l6ZSA9IDEyKSwgIA0KICAgIGxlZ2VuZC50aXRsZSA9IGVsZW1lbnRfdGV4dChzaXplID0gMTQsIGZhY2UgPSAiYm9sZCIpLCAgDQogICAgbGVnZW5kLmtleS53aWR0aCA9IHVuaXQoMzAsICJtbSIpICANCiAgKSArDQogIHNjYWxlX2ZpbGxfZ3JhZGllbnQoDQogICAgbG93ID0gIiM5OEZCOTgiLCBoaWdoID0gIiMwMDY0MDAiLA0KICAgIG5hbWUgPSAiU2NvcmUiLCBuYS52YWx1ZSA9ICJncmF5NzAiLA0KICAgIGxpbWl0cyA9IGMoMSwgMjApKSArDQogIGd1aWRlcygNCiAgICBmaWxsID0gZ3VpZGVfY29sb3VyYmFyKA0KICAgICAgYmFyd2lkdGggPSB1bml0KDE4MCwgdW5pdHMgPSAibW0iKSwNCiAgICAgIGJhcmhlaWdodCA9IHVuaXQoMywgdW5pdHMgPSAibW0iKQ0KICAgICkNCiAgKQ0KDQpmaWc1DQoNCiMgZ2dzYXZlKGhlcmUoImZpZ3VyZXMiLCAiZmlnNS5wZGYiKSwgd2lkdGggPSAyMSwgaGVpZ2h0ID0gMTIsIHVuaXRzID0gImNtIiwgc2NhbGUgPSAyLCBkcGkgPSA4MDApDQojIGdnc2F2ZShoZXJlKCJmaWd1cmVzIiwgImZpZzUuanBnIiksIHdpZHRoID0gMjEsIGhlaWdodCA9IDEyLCB1bml0cyA9ICJjbSIsIHNjYWxlID0gMiwgZHBpID0gODAwKQ0KDQpgYGANCg0KIyMgTWFwIG9mIGV1cm9wZSANCmBgYHtyfQ0KZmlnNWYgPC0gZnVsbG1hcCAlPiUNCmdncGxvdChhZXMoZmlsbCA9IG4sIG1hcF9pZCA9IHJlZ2lvbikpICsNCmdlb21fbWFwKG1hcCA9IHdvcmxkX21hcCwgY29sb3IgPSAiZ3JheTUwIikgKw0KY29vcmRfbWFwKCJtZXJjYXRvciIsIHlsaW0gPSBjKDMwLCA2NSksIHhsaW0gPSBjKC0yNSwgNDUpKSArICMgc2V0IGxpbWl0cyBmb3IgRXVyb3BlDQp0aGVtZShsZWdlbmQucG9zaXRpb24gPSAicmlnaHQiKSArDQpzY2FsZV9maWxsX2dyYWRpZW50KGxvdyA9ICIjOThGQjk4IiwgaGlnaCA9ICIjMDA2NDAwIiwNCm5hbWUgPSAiU2NvcmUiLCBuYS52YWx1ZSA9ICJncmF5NzAiLA0KbGltaXRzID0gYygxLCAxMCksDQpndWlkZSA9IGd1aWRlX2NvbG9yYmFyKGRpcmVjdGlvbiA9ICJ2ZXJ0aWNhbC4iKSkgKw0KZ3VpZGVzKGZpbGwgPSBndWlkZV9jb2xvdXJiYXIoYmFyd2lkdGggPSB1bml0KDEwLCB1bml0cyA9ICJtbSIpLCBiYXJoZWlnaHQgPSB1bml0KDIwLCB1bml0cyA9ICJtbSIpKSkgKw0KdGhlbWUoYXhpcy50ZXh0LnggPSBlbGVtZW50X2JsYW5rKCksDQpheGlzLnRleHQueSA9IGVsZW1lbnRfYmxhbmsoKSwNCmF4aXMudGl0bGUueCA9IGVsZW1lbnRfYmxhbmsoKSwNCmF4aXMudGl0bGUueSA9IGVsZW1lbnRfYmxhbmsoKSwNCnBhbmVsLmdyaWQubWFqb3IgPSBlbGVtZW50X2JsYW5rKCksDQpwYW5lbC5ncmlkLm1pbm9yID0gZWxlbWVudF9ibGFuaygpLA0KcGFuZWwuYmFja2dyb3VuZCA9IGVsZW1lbnRfYmxhbmsoKSkNCg0KZmlnNWYNCg0KDQpgYGANCg0KIyMgZmlnNWYgLSBjb3VudHJ5IGNvbGxhYm9yYXRpb24gbmV0d29yayBjaXJjbGUgcGxvdA0KYGBge3J9DQojIEV4dHJhY3QgY291bnRyaWVzIGZyb20gdGhlIGFmZmlsaWF0aW9ucw0KYmliX3NjbzIgPC0gbWV0YVRhZ0V4dHJhY3Rpb24oYmliX3NjbywgRmllbGQgPSAiQVVfQ08iLCBzZXAgPSAiOyIpDQoNCiMgQ3JlYXRlIGEgbmV0d29yayBtYXRyaXggb2YgY29sbGFib3JhdGlvbnMgYmV0d2VlbiBjb3VudHJpZXMNCk5ldE1hdHJpeF9jb3VudHJ5IDwtIGJpYmxpb05ldHdvcmsoYmliX3NjbzIsIGFuYWx5c2lzID0gImNvbGxhYm9yYXRpb24iLCBuZXR3b3JrID0gImNvdW50cmllcyIsIHNlcCA9ICI7IikNCg0KIyBDb252ZXJ0IHRoZSBuZXR3b3JrIG1hdHJpeCB0byBhIHN0YW5kYXJkIG1hdHJpeA0KTmV0TWF0cml4X2NvdW50cnkgPC0gYXMubWF0cml4KE5ldE1hdHJpeF9jb3VudHJ5KQ0KDQojIFJlbW92ZSB0aGUgbG93ZXIgdHJpYW5nbGUgKGFzIHRoaXMgaXMgZHVwbGljYXRpb24gb2YgaW5mbykNCk5ldE1hdHJpeF9jb3VudHJ5W2xvd2VyLnRyaShOZXRNYXRyaXhfY291bnRyeSldIDwtIDAgDQoNCiMgQ2hhbmdlIGNvbHVtbiBhbmQgcm93IG5hbWVzIHRvIHRpdGxlIGNhc2UNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb3VudHJ5KSA8LSBzdHJfdG9fdGl0bGUoY29sbmFtZXMoTmV0TWF0cml4X2NvdW50cnkpKQ0Kcm93bmFtZXMoTmV0TWF0cml4X2NvdW50cnkpIDwtIHN0cl90b190aXRsZShyb3duYW1lcyhOZXRNYXRyaXhfY291bnRyeSkpDQoNCiMgQ2hhbmdlICJVc2EiIHRvICJVU0EiDQpjb2xuYW1lcyhOZXRNYXRyaXhfY291bnRyeSlbY29sbmFtZXMoTmV0TWF0cml4X2NvdW50cnkpID09ICJVc2EiXSA8LSAiVVNBIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvdW50cnkpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb3VudHJ5KSA9PSAiVXNhIl0gPC0gIlVTQSINCg0KIyBDaGFuZ2UgIlVuaXRlZCBLaW5nZG9tIiB0byAiVUsiIGZvciBlYXNpZXIgcGxvdHRpbmcNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb3VudHJ5KVtjb2xuYW1lcyhOZXRNYXRyaXhfY291bnRyeSkgPT0gIlVuaXRlZCBLaW5nZG9tIl0gPC0gIlVLIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvdW50cnkpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb3VudHJ5KSA9PSAiVW5pdGVkIEtpbmdkb20iXSA8LSAiVUsiDQoNCiMgRGVmaW5lIGNvbG9ycyBmb3IgZWFjaCBjb3VudHJ5DQpteS5jb2xzMiA8LSBjKA0KICBVU0EgPSAiIzM3N2ViOCIsDQogIFNwYWluID0gIiNmZmZmMzMiLA0KICBDaGluYSA9ICIjZTQxYTFjIiwNCiAgRnJhbmNlID0gIiM5OTk5OTkiLA0KICBDYW5hZGEgPSAiI2E2Y2VlMyIsDQogIERlbm1hcmsgPSAiI2IyZGY4YSIsDQogIE5ldGhlcmxhbmRzID0gIiMzNzdlYjgiLA0KICBCZWxnaXVtID0gIiM5ODRlYTMiLA0KICBVSyA9ICIjZmZmZjMzIiwNCiAgQXVzdHJhbGlhID0gIiM0ZGFmNGEiLA0KICBCcmF6aWwgPSAiIzRkYWY0YSIsDQogIEdlcm1hbnkgPSAiI2IyZGY4YSIsDQogIEdyZWVjZSA9ICIjZjc4MWJmIiwNCiAgS29yZWEgPSAiI2Y3ODFiZiIsDQogIElyZWxhbmQgPSAiI2E2NTYyOCIsDQogIE5vcndheSA9ICIjZmY3ZjAwIiwNCiAgU3dlZGVuID0gIiM0ZGFmNGEiLA0KICBFZ3lwdCA9ICIjZjc4MWJmIiwNCiAgSXRhbHkgPSAiI2U0MWExYyIsDQogIEphcGFuID0gIiMxZjc4YjQiLA0KICBTd2l0emVybGFuZCA9ICIjOTg0ZWEzIiwNCiAgVHVya2V5ID0gIiMzM2EwMmMiLA0KICBBdXN0cmlhID0gIiNiMmRmOGEiLA0KICBJc3JhZWwgPSAiI2Y3ODFiZiIsDQogIE5ld1plYWxhbmQgPSAiIzRkYWY0YSIsDQogIFJ1c3NpYSA9ICIjOTk5OTk5IiwNCiAgU2luZ2Fwb3JlID0gIiNiMmRmOGEiLA0KICBQb3J0dWdhbCA9ICIjOTg0ZWEzIiwNCiAgRmlubGFuZCA9ICIjYjJkZjhhIiwNCiAgTWV4aWNvID0gIiNhNjU2MjgiLA0KICBQb2xhbmQgPSAiI2IyZGY4YSIsDQogIFNvdXRoQWZyaWNhID0gIiNmNzgxYmYiLA0KICBBcmdlbnRpbmEgPSAiI2ZmN2YwMCIsDQogIENoaWxlID0gIiNmZjdmMDAiLA0KICBDemVjaFJlcHVibGljID0gIiNiMmRmOGEiLA0KICBJY2VsYW5kID0gIiNiMmRmOGEiLA0KICBQZXJ1ID0gIiNmZjdmMDAiLA0KICBSb21hbmlhID0gIiNmYjlhOTkiLA0KICBTZXJiaWEgPSAiI2ZiOWE5OSIsDQogIFVBRSA9ICIjYTY1NjI4Ig0KKQ0KDQojIFNldHRpbmcgdXAgY3VzdG9tIHBhcmFtZXRlcnMNCmNpcmNvcy5wYXIoY2VsbC5wYWRkaW5nID0gYygwLCAwLCAwLCAwKSwgdHJhY2subWFyZ2luID0gYygwLCAwKSkNCg0KIyBDcmVhdGUgYSBjaG9yZCBkaWFncmFtIG9mIHRoZSBuZXR3b3JrIG1hdHJpeA0KZmlnNWYgPC0gY2hvcmREaWFncmFtKE5ldE1hdHJpeF9jb3VudHJ5LCBhbm5vdGF0aW9uVHJhY2sgPSAiZ3JpZCIsIHByZUFsbG9jYXRlVHJhY2tzID0gMSwgZ3JpZC5jb2wgPSBteS5jb2xzMikNCg0KIyBBZGQgYSB0cmFjayB0byBsYWJlbCBlYWNoIHNlY3RvciB3aXRoIGl0cyBuYW1lDQpjaXJjb3MudHJhY2tQbG90UmVnaW9uKHRyYWNrLmluZGV4ID0gMSwgYmcuYm9yZGVyID0gTkEsIHBhbmVsLmZ1biA9IGZ1bmN0aW9uKHgsIHkpIHsNCiAgeGxpbSA9IGdldC5jZWxsLm1ldGEuZGF0YSgieGxpbSIpDQogIHlsaW0gPSBnZXQuY2VsbC5tZXRhLmRhdGEoInlsaW0iKQ0KICBzZWN0b3IubmFtZSA9IGdldC5jZWxsLm1ldGEuZGF0YSgic2VjdG9yLmluZGV4IikNCiAgY2lyY29zLnRleHQobWVhbih4bGltKSwgeWxpbVsxXSArIDAuMiAsIHNlY3Rvci5uYW1lLCBmYWNpbmcgPSAiY2xvY2t3aXNlIiwgbmljZUZhY2luZyA9IFRSVUUsIGFkaiA9IGMoMCwgMCkpDQogIGNpcmNvcy5heGlzKGggPSAidG9wIiwgbGFiZWxzLmNleCA9IDAuNSwgbWFqb3IudGljay5sZW5ndGggPSAwLjIsIHNlY3Rvci5pbmRleCA9IHNlY3Rvci5uYW1lLCB0cmFjay5pbmRleCA9IDIpDQp9KQ0KDQpgYGANCg0KIyMgZmlnNWcgY29sbGFib3JhdGlvbiBtYXRyaXggd2l0aCBzZWxmIGNpdGF0aW9uIHJlbW92ZWQNCmBgYHtyfQ0KDQpkaWFnKE5ldE1hdHJpeF9jb3VudHJ5KSA8LSAwDQoNCiMgQ3JlYXRlIGEgY2hvcmQgZGlhZ3JhbSBvZiB0aGUgbmV0d29yayBtYXRyaXgNCmZpZzVnIDwtIGNob3JkRGlhZ3JhbShOZXRNYXRyaXhfY291bnRyeSwgYW5ub3RhdGlvblRyYWNrID0gImdyaWQiLCBwcmVBbGxvY2F0ZVRyYWNrcyA9IDEsIGdyaWQuY29sID0gbXkuY29sczIpDQoNCiMgQWRkIGEgdHJhY2sgdG8gbGFiZWwgZWFjaCBzZWN0b3Igd2l0aCBpdHMgbmFtZQ0KY2lyY29zLnRyYWNrUGxvdFJlZ2lvbih0cmFjay5pbmRleCA9IDEsIHBhbmVsLmZ1biA9IGZ1bmN0aW9uKHgsIHkpIHsNCiAgeGxpbSA9IGdldC5jZWxsLm1ldGEuZGF0YSgieGxpbSIpDQogIHlsaW0gPSBnZXQuY2VsbC5tZXRhLmRhdGEoInlsaW0iKQ0KICBzZWN0b3IubmFtZSA9IGdldC5jZWxsLm1ldGEuZGF0YSgic2VjdG9yLmluZGV4IikNCiAgY2lyY29zLnRleHQobWVhbih4bGltKSwgeWxpbVsxXSArIDAuMiwgc2VjdG9yLm5hbWUsIGZhY2luZyA9ICJjbG9ja3dpc2UiLCBuaWNlRmFjaW5nID0gVFJVRSwgYWRqID0gYygwLCAwLjUpKQ0KICBjaXJjb3MuYXhpcyhoID0gInRvcCIsIGxhYmVscy5jZXggPSAwLjUsIG1ham9yLnRpY2subGVuZ3RoID0gMC4yLCBzZWN0b3IuaW5kZXggPSBzZWN0b3IubmFtZSwgdHJhY2suaW5kZXggPSAyKQ0KfSwgYmcuYm9yZGVyID0gTkEpDQpgYGANCg0KIyMgZmlnIDVoIGNvbnRpdG5lbnQgY29sbGFib3JhdGlvbiANCmBgYHtyfQ0KDQoNCk5ldE1hdHJpeF9jb250aW5lbnQgPC0gTmV0TWF0cml4X2NvdW50cnkNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJVU0EiXSA8LSAiTm9ydGggQW1lcmljYSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJVU0EiXSA8LSAiTm9ydGggQW1lcmljYSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIlNwYWluIl0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJTcGFpbiJdIDwtICJFdXJvcGUiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJDaGluYSJdIDwtICJBc2lhIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkNoaW5hIl0gPC0gIkFzaWEiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJGcmFuY2UiXSA8LSAiRXVyb3BlIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkZyYW5jZSJdIDwtICJFdXJvcGUiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJDYW5hZGEiXSA8LSAiTm9ydGggQW1lcmljYSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJDYW5hZGEiXSA8LSAiTm9ydGggQW1lcmljYSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkRlbm1hcmsiXSA8LSAiRXVyb3BlIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkRlbm1hcmsiXSA8LSAiRXVyb3BlIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiTmV0aGVybGFuZHMiXSA8LSAiRXVyb3BlIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIk5ldGhlcmxhbmRzIl0gPC0gIkV1cm9wZSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkJlbGdpdW0iXSA8LSAiRXVyb3BlIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkJlbGdpdW0iXSA8LSAiRXVyb3BlIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiVUsiXSA8LSAiRXVyb3BlIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIlVLIl0gPC0gIkV1cm9wZSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkF1c3RyYWxpYSJdIDwtICJBdXN0cmFsaWEiDQpyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiQXVzdHJhbGlhIl0gPC0gIkF1c3RyYWxpYSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkJyYXppbCJdIDwtICJTb3V0aCBBbWVyaWNhIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkJyYXppbCJdIDwtICJTb3V0aCBBbWVyaWNhIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiR2VybWFueSJdIDwtICJFdXJvcGUiDQpyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiR2VybWFueSJdIDwtICJFdXJvcGUiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJGaW5sYW5kIl0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJGaW5sYW5kIl0gPC0gIkV1cm9wZSINCg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiR3JlZWNlIl0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJHcmVlY2UiXSA8LSAiRXVyb3BlIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiS29yZWEiXSA8LSAiQXNpYSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJLb3JlYSJdIDwtICJBc2lhIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiTm9yd2F5Il0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJOb3J3YXkiXSA8LSAiRXVyb3BlIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiU3dlZGVuIl0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJTd2VkZW4iXSA8LSAiRXVyb3BlIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiRWd5cHQiXSA8LSAiQWZyaWNhIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkVneXB0Il0gPC0gIkFmcmljYSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkl0YWx5Il0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJJdGFseSJdIDwtICJFdXJvcGUiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJKYXBhbiJdIDwtICJBc2lhIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkphcGFuIl0gPC0gIkFzaWEiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJQb3J0dWdhbCJdIDwtICJFdXJvcGUiDQpyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiUG9ydHVnYWwiXSA8LSAiRXVyb3BlIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiU3dpdHplcmxhbmQiXSA8LSAiRXVyb3BlIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIlN3aXR6ZXJsYW5kIl0gPC0gIkV1cm9wZSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIlR1cmtleSJdIDwtICJBc2lhIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIlR1cmtleSJdIDwtICJBc2lhIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiSW5kaWEiXSA8LSAiQXNpYSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJJbmRpYSJdIDwtICJBc2lhIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiSXJhbiJdIDwtICJBc2lhIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIklyYW4iXSA8LSAiQXNpYSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkNvc3RhIFJpY2EiXSA8LSAiTm9ydGggQW1lcmljYSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJDb3N0YSBSaWNhIl0gPC0gIk5vcnRoIEFtZXJpY2EiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJDemVjaCBSZXB1YmxpYyJdIDwtICJFdXJvcGUiDQpyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiQ3plY2ggUmVwdWJsaWMiXSA8LSAiRXVyb3BlIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiSG9uZyBLb25nIl0gPC0gIkFzaWEiDQpyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiSG9uZyBLb25nIl0gPC0gIkFzaWEiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJJY2VsYW5kIl0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJJY2VsYW5kIl0gPC0gIkV1cm9wZSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIklyZWxhbmQiXSA8LSAiRXVyb3BlIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIklyZWxhbmQiXSA8LSAiRXVyb3BlIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiTWV4aWNvIl0gPC0gIk5vcnRoIEFtZXJpY2EiDQpyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtyb3duYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiTWV4aWNvIl0gPC0gIk5vcnRoIEFtZXJpY2EiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJSb21hbmlhIl0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJSb21hbmlhIl0gPC0gIkV1cm9wZSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIlNsb3Zha2lhIl0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJTbG92YWtpYSJdIDwtICJFdXJvcGUiDQoNCmNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW2NvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJVa3JhaW5lIl0gPC0gIkV1cm9wZSINCnJvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpW3Jvd25hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpID09ICJVa3JhaW5lIl0gPC0gIkV1cm9wZSINCg0KY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbY29sbmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkF1c3RyYWxpYSJdIDwtICJPY2VhbmlhIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkF1c3RyYWxpYSJdIDwtICJPY2VhbmlhIg0KDQpjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KVtjb2xuYW1lcyhOZXRNYXRyaXhfY29udGluZW50KSA9PSAiS2F6YWtoc3RhbiJdIDwtICJBc2lhIg0Kcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudClbcm93bmFtZXMoTmV0TWF0cml4X2NvbnRpbmVudCkgPT0gIkthemFraHN0YW4iXSA8LSAiQXNpYSINCg0KDQojIGNvbGxhcHNpbmcNCm1lcmdlX21hdHJpeCA8LSB0KHJvd3N1bSh0KE5ldE1hdHJpeF9jb250aW5lbnQpLCBncm91cCA9IGNvbG5hbWVzKE5ldE1hdHJpeF9jb250aW5lbnQpLCBuYS5ybSA9IFQpKQ0KbWVyZ2VfbWF0cml4MiA8LSByb3dzdW0obWVyZ2VfbWF0cml4LCBncm91cCA9IHJvd25hbWVzKG1lcmdlX21hdHJpeCkpDQojIHJlbW92ZSBkaWFnb25hbCBlbGVtZW50cw0KZGlhZyhtZXJnZV9tYXRyaXgyKSA8LSAwDQojIGNob3JkIHBsb3QNCmNob3JkRGlhZ3JhbUZyb21NYXRyaXgobWVyZ2VfbWF0cml4MikNCg0KIyBEZWZpbmUgY29sb3JzIGZvciBlYWNoIGNvbnRpbmVudA0KbXkuY29sczIgPC0gYygNCiAgQWZyaWNhID0gIiNDQzc5QTciLA0KICBOb3J0aEFtZXJpY2EgPSAiI0YwRTQ0MiIsDQogIEFzaWEgPSAiIzAwNzJCMiIsDQogIEV1cm9wZSA9ICIjRTY5RjAwIiwNCiAgT2NlYW5pYSA9ICIjMDA5RTczIiwNCiAgU291dGhBbWVyaWNhID0gIiNENTVFMDAiDQopDQoNCg0KIyBDcmVhdGUgYSBjaG9yZCBkaWFncmFtIG9mIHRoZSBuZXR3b3JrIG1hdHJpeA0KZmlnNWggPC0gY2hvcmREaWFncmFtKG1lcmdlX21hdHJpeDIsIGFubm90YXRpb25UcmFjayA9ICJncmlkIiwgcHJlQWxsb2NhdGVUcmFja3MgPSAxKQ0KIyBBZGQgYSB0cmFjayB0byBsYWJlbCBlYWNoIHNlY3RvciB3aXRoIGl0cyBuYW1lDQpjaXJjb3MudHJhY2tQbG90UmVnaW9uKHRyYWNrLmluZGV4ID0gMSwgcGFuZWwuZnVuID0gZnVuY3Rpb24oeCwgeSkgew0KICB4bGltID0gZ2V0LmNlbGwubWV0YS5kYXRhKCJ4bGltIikNCiAgeWxpbSA9IGdldC5jZWxsLm1ldGEuZGF0YSgieWxpbSIpDQogIHNlY3Rvci5uYW1lID0gZ2V0LmNlbGwubWV0YS5kYXRhKCJzZWN0b3IuaW5kZXgiKQ0KICBjaXJjb3MudGV4dChtZWFuKHhsaW0pLCB5bGltWzFdICsgMC4yLCBzZWN0b3IubmFtZSwgZmFjaW5nID0gImNsb2Nrd2lzZSIsIG5pY2VGYWNpbmcgPSBUUlVFLCBhZGogPSBjKDAsIDAuNSkpDQogIGNpcmNvcy5heGlzKGggPSAidG9wIiwgbGFiZWxzLmNleCA9IDAuNSwgbWFqb3IudGljay5sZW5ndGggPSAwLjIsIHNlY3Rvci5pbmRleCA9IHNlY3Rvci5uYW1lLCB0cmFjay5pbmRleCA9IDIpDQp9LCBiZy5ib3JkZXIgPSBOQSkNCg0KYGBgDQoNCiMjIGRpc2NpcGxpbmUgY29sbGFiDQoNCmBgYHtyfQ0KRmllbGRzIDwtIHNkICU+JQ0KICBtdXRhdGUoDQogICAgdGl0bGUgPSBzdHJfdG9fbG93ZXIocGFwZXJfdGl0bGUpLA0KICAgIG50aXRsZSA9IHBhc3RlKHN0cl90b19sb3dlcihzdHJfc3BsaXRfZml4ZWQoc3R1ZHlfaWQsICJcXF8iLCBuID0gMilbLDFdKSwgcGFwZXJfdGl0bGUsIHNlcCA9ICIgIiksDQogICAgbnRpdGxlID0gc3RyX3NxdWlzaChudGl0bGUpDQogICkgJT4lIA0KICBzZWxlY3QobnRpdGxlLCBKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCkNCg0KQmliX25hbWVzIDwtIGJpYl9zY28gJT4lIHJvd25hbWVzX3RvX2NvbHVtbiguLCB2YXIgPSAibWF0X25hbWVzIikgJT4lIA0KICBtdXRhdGUoVEkyID0gdG9sb3dlcih1bmxpc3QobGFwcGx5KGRhdGEuZnJhbWUodChzdHJfc3BsaXRfZml4ZWQoVEksICIgIiwgbiA9IDE1KVssMToxNF0pKSwgDQogICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgZnVuY3Rpb24oeCkgc3RyX2MoeCwgY29sbGFwc2UgID0gIiAiKSkpKSwNCiAgICAgICAgICMgc3RyaV90cmFuc19nZW5lcmFsID0gZ2V0dGluZyByaWQgb2Ygc3BlY2lhbCBsZXR0ZXJzDQogICAgICAgICBuYW1lMiA9IHN0cmlfdHJhbnNfZ2VuZXJhbCh0b2xvd2VyKHN0cl9zcGxpdF9maXhlZChTUiwgIiAiLCBuID0gMilbLDFdKSwgImxhdGluLWFzY2lpIiksDQogICAgICAgICBUSTIgPSBwYXN0ZShuYW1lMiwgVEkyLCBzZXA9ICIgIiksDQogICAgICAgICBUSTIgPSB0cmltd3MoVEkyKSkgJT4lIA0KICBzZWxlY3QoVEkyLCBtYXRfbmFtZXMpDQoNCiNzdHJpbmdkaXN0KEJpYl9uYW1lcyRUSTIsIEZpZWxkcyRudGl0bGVbMV0sIG1ldGhvZCA9ICdvc2EnKQ0KcG9zIDwtIGxhcHBseShCaWJfbmFtZXMkVEkyLCBmdW5jdGlvbih4KSBzdHJpbmdkaXN0KEZpZWxkcyRudGl0bGUsIHgpKQ0KcG9zMjwtIG1hcF9kYmwocG9zLCB3aGljaC5taW4pDQoNCiMgdGhlc2UgYXJlIGxvb2tpbmcgZ29vZCAtIGJvdGggaGF2ZSB0aGUgcGVyZmVjdCBtYXRjaGVzIChhdCBsZWFzdCBhdCBhIGdsYW5jZSkNCkJpYl9uYW1lcyRUSTINCkZpZWxkcyRudGl0bGVbcG9zMl0NCg0KIyBub3cgd2UgY2FuIG1lcmdlIHR3byBkYXRhc2V0cyANCkJpYl9uYW1lcyRKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZCA8LSBGaWVsZHMkSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWRbcG9zMl0NCg0KIyBDcmVhdGluZyBtYXRyaXggZm9yIGJpYmxpb21ldHJpYyBjb3VwbGluZw0KTmV0TWF0cml4IDwtIGJpYmxpb05ldHdvcmsoYmliX3NjbywgYW5hbHlzaXMgPSAiY291cGxpbmciLCBuZXR3b3JrID0gInJlZmVyZW5jZXMiLCBzZXAgPSAiOyIpDQoNCiMgZm9yY2luZyBpbnRvIGEgbnJvbWFsIG1hdHJpeA0KbmV0X21hdHJpeCA8LSBhcy5tYXRyaXgoTmV0TWF0cml4KQ0KZGlhZyhuZXRfbWF0cml4KSA8LSAwICNnZXQgcmlkIG9mIGNvdW50cyBmb3IgdGhlIHNhbWUgcGFwZXJzDQoNCiMgcmVwbGFjaW5nIG5hbWVzIHdpdGggSm91cm5hbF9DYXRlZ29yeV9BbGxvY2F0ZWRfQnJvYWQNCnJvd25hbWVzKG5ldF9tYXRyaXgpIDwtIEJpYl9uYW1lcyRKb3VybmFsX0NhdGVnb3J5X0FsbG9jYXRlZF9Ccm9hZA0KY29sbmFtZXMobmV0X21hdHJpeCkgPC0gQmliX25hbWVzJEpvdXJuYWxfQ2F0ZWdvcnlfQWxsb2NhdGVkX0Jyb2FkDQoNCg0KDQoNCg0KIyByZWR1Y2luZyBtYXRyaXggYWNjb3JkaW5nIHRvIGRpc2NpcGxpbmVfY29kZQ0KcmVjdF9tYXRyaXg8LSB0KHJvd3N1bSh0KG5ldF9tYXRyaXgpLCBncm91cCA9IGNvbG5hbWVzKG5ldF9tYXRyaXgpLCBuYS5ybSA9IFQpKQ0Kc21hbGxfbWF0cml4IDwtIHJvd3N1bShyZWN0X21hdHJpeCwgZ3JvdXAgPSByb3duYW1lcyhyZWN0X21hdHJpeCkpDQoNCiMgZ2V0dGluZyByaWQgb2YgbG93ZXIgdHJpYW5nbGUgKGFzIHRoaXMgaXMgZHVwbGljYXRpb24gb2YgaW5mbykNCnNtYWxsX21hdHJpeFtsb3dlci50cmkoc21hbGxfbWF0cml4KV0gPC0gMCANCg0KDQpwYXIobWFyID0gYygwLCAwLCAwLCAwKSwgbWZyb3cgPSBjKDEsIDEpKQ0KDQoNCiMgQ3JlYXRlIGEgY2hvcmQgZGlhZ3JhbSBvZiB0aGUgbmV0d29yayBtYXRyaXgNCmZpZzVoIDwtIGNob3JkRGlhZ3JhbShzbWFsbF9tYXRyaXgsIGFubm90YXRpb25UcmFjayA9ICJncmlkIiwgcHJlQWxsb2NhdGVUcmFja3MgPSAxKQ0KIyBBZGQgYSB0cmFjayB0byBsYWJlbCBlYWNoIHNlY3RvciB3aXRoIGl0cyBuYW1lDQpjaXJjb3MudHJhY2tQbG90UmVnaW9uKHRyYWNrLmluZGV4ID0gMSwgcGFuZWwuZnVuID0gZnVuY3Rpb24oeCwgeSkgew0KICB4bGltID0gZ2V0LmNlbGwubWV0YS5kYXRhKCJ4bGltIikNCiAgeWxpbSA9IGdldC5jZWxsLm1ldGEuZGF0YSgieWxpbSIpDQogIHNlY3Rvci5uYW1lID0gZ2V0LmNlbGwubWV0YS5kYXRhKCJzZWN0b3IuaW5kZXgiKQ0KICBjaXJjb3MudGV4dChtZWFuKHhsaW0pLCB5bGltWzFdICsgMC4yLCBzZWN0b3IubmFtZSwgZmFjaW5nID0gImNsb2Nrd2lzZSIsIG5pY2VGYWNpbmcgPSBUUlVFLCBhZGogPSBjKDAsIDAuNSkpDQogIGNpcmNvcy5heGlzKGggPSAidG9wIiwgbGFiZWxzLmNleCA9IDAuNSwgbWFqb3IudGljay5sZW5ndGggPSAwLjIsIHNlY3Rvci5pbmRleCA9IHNlY3Rvci5uYW1lLCB0cmFjay5pbmRleCA9IDIpDQp9LCBiZy5ib3JkZXIgPSBOQSkNCg0KDQpgYGANCg0KDQpgYGB7cn0NCmRpYWcoc21hbGxfbWF0cml4KSA8LSAwDQoNCiMgQ3JlYXRlIGEgY2hvcmQgZGlhZ3JhbSBvZiB0aGUgbmV0d29yayBtYXRyaXgNCmZpZzVnIDwtIGNob3JkRGlhZ3JhbShzbWFsbF9tYXRyaXgsIGFubm90YXRpb25UcmFjayA9ICJncmlkIiwgcHJlQWxsb2NhdGVUcmFja3MgPSAxKQ0KDQojIEFkZCBhIHRyYWNrIHRvIGxhYmVsIGVhY2ggc2VjdG9yIHdpdGggaXRzIG5hbWUNCmNpcmNvcy50cmFja1Bsb3RSZWdpb24odHJhY2suaW5kZXggPSAxLCBwYW5lbC5mdW4gPSBmdW5jdGlvbih4LCB5KSB7DQogIHhsaW0gPSBnZXQuY2VsbC5tZXRhLmRhdGEoInhsaW0iKQ0KICB5bGltID0gZ2V0LmNlbGwubWV0YS5kYXRhKCJ5bGltIikNCiAgc2VjdG9yLm5hbWUgPSBnZXQuY2VsbC5tZXRhLmRhdGEoInNlY3Rvci5pbmRleCIpDQogIGNpcmNvcy50ZXh0KG1lYW4oeGxpbSksIHlsaW1bMV0gKyAuMSwgc2VjdG9yLm5hbWUsIGZhY2luZyA9ICJjbG9ja3dpc2UiLCBuaWNlRmFjaW5nID0gVFJVRSwgYWRqID0gYygwLCAwLjUpKQ0KICBjaXJjb3MuYXhpcyhoID0gInRvcCIsIGxhYmVscy5jZXggPSAwLjUsIG1ham9yLnRpY2subGVuZ3RoID0gMC4yLCBzZWN0b3IuaW5kZXggPSBzZWN0b3IubmFtZSwgdHJhY2suaW5kZXggPSAyKQ0KfSwgYmcuYm9yZGVyID0gTkEpDQpgYGANCg0KYGBge3IgbW9zdCBjaXRlZCBhcnRpY2xlcyBhbmQgYXV0aG9yc30NCg0KQ1IgPC0gY2l0YXRpb25zKGJpYl9zY28sIGZpZWxkID0gImFydGljbGUiLCBzZXAgPSAiOyIpICNsaXN0IG9mIG1vc3QgY2l0ZWQgYXJ0aWNsZXMNCiBjYmluZChDUiRDaXRlZFsxOjEwXSkgI3RlbiBtb3N0IGNpdGVkIGFydGljbGVzDQogDQpDUiA8LSBjaXRhdGlvbnMoYmliX3NjbywgZmllbGQgPSAiYXV0aG9yIiwgc2VwID0gIjsiKQ0KY2JpbmQoQ1IkQ2l0ZWRbMToxMF0pICN0ZW4gbW9zdCBjaXRlZCBhdXRob3JzDQpgYGAgDQoNCmBgYHtyIGJpYmxpb21ldHJpYyBjb3VwbGluZyBuZXR3b3JrfQ0KTmV0TWF0cml4X2NvdXBsaW5nIDwtIGJpYmxpb05ldHdvcmsoYmliX3NjbywgYW5hbHlzaXMgPSAiY291cGxpbmciLCBuZXR3b3JrID0gInJlZmVyZW5jZXMiLCBzZXAgPSAiOyAiKQ0KTmV0TWF0cml4X2NvdXBsaW5nX3Bsb3QgPC0gbmV0d29ya1Bsb3QoTmV0TWF0cml4X2NvdXBsaW5nLCBuID0gMjAsIA0KICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgVGl0bGUgPSAiUGFwZXIgY28tY2l0YXRpb24iLCB0eXBlID0gImZydWNodGVybWFuIiwgc2l6ZT1ULCANCiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHJlbW92ZS5tdWx0aXBsZT1GQUxTRSwgbGFiZWxzaXplPTAuOCxlZGdlc2l6ZSA9IDUpDQpgYGANCg0KDQo=